Создаём свой слайдер на чистом JavaScript: от нуля до плавных переходов

Создаём свой слайдер на чистом JavaScript: от нуля до плавных переходов

Слайдеры — неотъемлемая часть современного веба, но зачем тянуть тяжёлую библиотеку ради нескольких изображений? В этом руководстве мы с нуля создадим карусель на чистом JavaScript, разберём механику переключения, добавим плавные анимации и пагинацию, а вы поймёте, что иногда лучший инструмент — тот, что сделали вы сами.

Зачем писать слайдер самостоятельно?

Библиотеки вроде Slick или Swiper — это удобно, но они добавляют лишние килобайты, могут конфликтовать с вашим кодом и часто содержат функционал, который вам не нужен. Свой слайдер будет легковесным, полностью контролируемым и отличным упражнением для понимания DOM, событий и CSS-анимаций.

Слайдер, созданный с нуля, обычно весит менее 5 КБ против 50+ КБ у популярных библиотек (без учёта зависимостей).

Структура HTML: основа карусели

Начнём с разметки. Нам понадобится контейнер, обёртка для слайдов и сами слайды.

<div class="slider-container">
  <div class="slider-track">
    <div class="slide"><img src="slide1.jpg" alt=""></div>
    <div class="slide"><img src="slide2.jpg" alt=""></div>
    <div class="slide"><img src="slide3.jpg" alt=""></div>
  </div>
  <button class="slider-btn prev">❮</button>
  <button class="slider-btn next">❯</button>
  <div class="slider-dots"></div>
</div>

Ключевые CSS-стили

С помощью CSS мы скроем всё, что выходит за пределы контейнера, и расположим слайды горизонтально.

.slider-container {
  position: relative;
  overflow: hidden;
  max-width: 800px;
  margin: 0 auto;
}
.slider-track {
  display: flex;
  transition: transform 0.5s ease-in-out;
}
.slide {
  min-width: 100%;
  height: 400px;
  object-fit: cover;
}

JavaScript: оживляем механику

Теперь самое интересное — логика переключения. Создадим объект слайдера с основными методами.

class SimpleSlider {
  constructor(containerSelector) {
    this.container = document.querySelector(containerSelector);
    this.track = this.container.querySelector('.slider-track');
    this.slides = Array.from(this.track.children);
    this.currentIndex = 0;
    this.initControls();
    this.updateTrack();
  }

  moveTo(index) {
    if (index < 0) index = this.slides.length - 1;
    if (index >= this.slides.length) index = 0;
    this.currentIndex = index;
    this.updateTrack();
  }

  updateTrack() {
    const offset = -this.currentIndex * 100;
    this.track.style.transform = `translateX(${offset}%)`;
  }

  initControls() {
    const nextBtn = this.container.querySelector('.next');
    const prevBtn = this.container.querySelector('.prev');
    nextBtn.addEventListener('click', () => this.moveTo(this.currentIndex + 1));
    prevBtn.addEventListener('click', () => this.moveTo(this.currentIndex - 1));
  }
}

// Инициализация
new SimpleSlider('.slider-container');

Используйте CSS-переход (transition) для анимации вместо JavaScript-интервалов. Это производительнее и плавнее.

Добавляем индикаторы и автопрокрутку

Слайдер без точек навигации и автопереключения — неполноценный. Реализуем эти функции.

Создание точек-индикаторов

createDots() {
  const dotsContainer = this.container.querySelector('.slider-dots');
  this.slides.forEach((_, index) => {
    const dot = document.createElement('button');
    dot.classList.add('dot');
    dot.addEventListener('click', () => this.moveTo(index));
    dotsContainer.appendChild(dot);
  });
  this.updateDots();
}

updateDots() {
  const dots = this.container.querySelectorAll('.dot');
  dots.forEach((dot, index) => {
    dot.classList.toggle('active', index === this.currentIndex);
  });
}

Автопрокрутка с паузой при наведении

startAutoPlay(interval = 3000) {
  this.autoPlayInterval = setInterval(() => {
    this.moveTo(this.currentIndex + 1);
  }, interval);

  this.container.addEventListener('mouseenter', () => clearInterval(this.autoPlayInterval));
  this.container.addEventListener('mouseleave', () => this.startAutoPlay(interval));
}

Оптимизация и расширение функционала

Готовый слайдер можно улучшить:

  • Добавить touch-события для свайпов на мобильных устройствах.
  • Реализовать бесконечную прокрутку через клонирование крайних слайдов.
  • Добавить ленивую загрузку изображений для повышения производительности.
  • Создать переходы с fade-эффектом вместо горизонтального сдвига.

FAQ: частые вопросы о самописных слайдерах

Сложно ли сделать слайдер на чистом JS?

Нет, базовая реализация занимает около 50 строк кода. Главное — понять принцип работы transform и управления DOM.

Будет ли такой слайдер работать в старых браузерах?

Да, если использовать подход с изменением margin-left вместо transform для анимации, но это менее производительно.

Как добавить вертикальную прокрутку?

Замените translateX на translateY и измените flex-direction у .slider-track на column.

Почему слайдер дёргается при быстром клике?

Добавьте флаг isAnimating, который блокирует обработку событий во время перехода.

Как реализовать адаптивность?

Используйте CSS-медиазапросы для изменения размеров .slider-container и обновляйте расчёты в JavaScript при resize.