Простой jQuery-скрипт для табов (вкладок)

Самый простой пример реализации табов на сайте. Код максимально простой и легкий, не нужно никаких сторонних библиотек (кроме jquery) и никакого лишнего громоздкого кода. Весь HTML можно поменять под свою верстку, только не забудьте тогда поменять и код в скрипте, и в CSS.

HTML для табов

<div class="tabs">
 
  <ul class="tabs__caption">
    <li class="active">1-я вкладка</li>
    <li>2-я вкладка</li>
  </ul>
 
  <div class="tabs__content active">
    Содержимое первого блока
  </div>
 
  <div class="tabs__content">
    Содержимое второго блока
  </div>
 
</div><!-- .tabs-->

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

Обязательные CSS-стили для вышеуказанного HTML-кода

.tabs__content {
  display: none; /* по умолчанию прячем все блоки */
}
.tabs__content.active {
  display: block; /* по умолчанию показываем нужный блок */
}

Для красивого отображения на сайте нужно использовать свои стили.

Подключаем jQuery перед скриптом

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>

JS-скрипт для табов

Данный код вы помещаете в свой файл скриптов, если такого нету, то создаете его, например, scripts.js и подключаете после jquery таким образом:

<script src="js/scripts.js"></script>

Содержимое скрипта:

(function($) {
$(function() {
 
  $('ul.tabs__caption').on('click', 'li:not(.active)', function() {
    $(this)
      .addClass('active').siblings().removeClass('active')
      .closest('div.tabs').find('div.tabs__content').removeClass('active').eq($(this).index()).addClass('active');
  });
 
});
})(jQuery);

Пример табов, в котором запоминается активная вкладка после перезагрузки страницы (с помощью cookie)

Пример табов, в котором запоминается активная вкладка после перезагрузки страницы (с помощью cookie). HTML и CSS остается тот же, меняется только скрипт.

$(function() {

  function createCookie(name,value,days) {
    if (days) {
      var date = new Date();
      date.setTime(date.getTime()+(days*24*60*60*1000));
      var expires = "; expires="+date.toGMTString();
    }
    else var expires = "";
    document.cookie = name+"="+value+expires+"; path=/";
  }
  function readCookie(name) {
    var nameEQ = name + "=";
    var ca = document.cookie.split(';');
    for(var i=0;i < ca.length;i++) {
      var c = ca[i];
      while (c.charAt(0)==' ') c = c.substring(1,c.length);
      if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length,c.length);
    }
    return null;
  }
  function eraseCookie(name) {
    createCookie(name,"",-1);
  }

  $('ul.tabs__caption').each(function(i) {
    var cookie = readCookie('tabCookie' + i);
    if (cookie) {
      $(this).find('li').removeClass('active').eq(cookie).addClass('active')
      .closest('div.tabs').find('div.tabs__content').removeClass('active').eq(cookie).addClass('active');
    }
  });

  $('ul.tabs__caption').on('click', 'li:not(.active)', function() {
    $(this)
    .addClass('active').siblings().removeClass('active')
    .closest('div.tabs').find('div.tabs__content').removeClass('active').eq($(this).index()).addClass('active');
    var ulIndex = $('ul.tabs__caption').index($(this).parents('ul.tabs__caption'));
    eraseCookie('tabCookie' + ulIndex);
    createCookie('tabCookie' + ulIndex, $(this).index(), 365);
  });

});
})(jQuery);

Пример табов, в котором запоминается активная вкладка после перезагрузки страницы (с помощью localStorage, меньше кода по сравнению с cookie)

Пример табов, в котором запоминается активная вкладка после перезагрузки страницы (с помощью localStorage, меньше кода по сравнению с cookie). HTML и CSS остается тот же, меняется только скрипт.

(function($) {
  $(function() {

    $('ul.tabs__caption').each(function(i) {
      var storage = localStorage.getItem('tab' + i);
      if (storage) {
        $(this).find('li').removeClass('active').eq(storage).addClass('active')
        .closest('div.tabs').find('div.tabs__content').removeClass('active').eq(storage).addClass('active');
      }
    });

    $('ul.tabs__caption').on('click', 'li:not(.active)', function() {
      $(this)
      .addClass('active').siblings().removeClass('active')
      .closest('div.tabs').find('div.tabs__content').removeClass('active').eq($(this).index()).addClass('active');
      var ulIndex = $('ul.tabs__caption').index($(this).parents('ul.tabs__caption'));
      localStorage.removeItem('tab' + ulIndex);
      localStorage.setItem('tab' + ulIndex, $(this).index());
    });

  });
})(jQuery);

Пример табов, в котором при переходе по ссылке с якорем, указывающим на номер таба, активируется соответствующий таб

Пример табов, в котором при переходе по ссылке с якорем, указывающим на номер таба, активируется соответствующий таб. HTML и CSS остается тот же, меняется только скрипт.

(function($) {
  $(function() {

    $('ul.tabs__caption').on('click', 'li:not(.active)', function() {
      $(this)
      .addClass('active').siblings().removeClass('active')
      .closest('div.tabs').find('div.tabs__content').removeClass('active').eq($(this).index()).addClass('active');
    });

    var tabIndex = window.location.hash.replace('#tab','')-1;
    if (tabIndex != -1) $('ul.tabs__caption li').eq(tabIndex).click();

    $('a[href*=#tab]').click(function() {
      var tabIndex = $(this).attr('href').replace(/(.*)#tab/, '')-1;
      $('ul.tabs__caption li').eq(tabIndex).click();
    });

  });
})(jQuery);

Полностью рабочий пример jquery-табов со своими стилями в вертикальном и горизонтальном виде:

See the Pen Jquery Tabs by Denis (@deniscreative) on CodePen.0

Сам скрипт целиком и полностью взят с сайта dimox.name

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

Чтобы далеко не ходить, сразу укажу, что остановился я на трех таких размерах для фавиконок,…

Фиксированное меню при прокрутке страницы только для мобильных

Немного другая вариация фиксированного меню. Меню фиксируется к верхней части экрана только на мобильных устройствах….

[CSS Animation] PCPP Loading Boxes

Красивая и не слишком сложная анимация, например, для загрузочной страницы сайта. HTML CSS Готовый пример:

Фиксированное меню при прокрутке страницы

Один из множества примеров сделать фиксированное меню при прокрутке. Пример упрощен, потому что хедер изначально…

23 комментария

Спасибо!

Aleksander

Спасибо большое)

После перебирания мегатонн говнокода наконец то я нашла НОРМАЛЬНЫЙ легкий корректный код и видит Всевышний, я не люблю плагиат, но я только учусь, а сама так не написала бы. Надеюсь, вы не очень сердитесь. что я его позаимствовала и зверски расковыряла) Но даже это он пережил и позволил реализовать табы в табах. Большое человеческое спасибо.

Максим

Для тех, кто учится, весь код — хороший. Нужно самому учиться писать не говнокод.

Огромное Вам спасибо! Вы мне сэкономили кучу времени!

А как сделать так что бы вкладка после обновления страницы оставалась на том же?

Нужно использовать немного другой скрипт, с использованием localStorage:

(function($) {
  $(function() {

    $('ul.tabs__caption').each(function(i) {
      var storage = localStorage.getItem('tab' + i);
      if (storage) {
        $(this).find('li').removeClass('active').eq(storage).addClass('active')
        .closest('div.tabs').find('div.tabs__content').removeClass('active').eq(storage).addClass('active');
      }
    });

    $('ul.tabs__caption').on('click', 'li:not(.active)', function() {
      $(this)
      .addClass('active').siblings().removeClass('active')
      .closest('div.tabs').find('div.tabs__content').removeClass('active').eq($(this).index()).addClass('active');
      var ulIndex = $('ul.tabs__caption').index($(this).parents('ul.tabs__caption'));
      localStorage.removeItem('tab' + ulIndex);
      localStorage.setItem('tab' + ulIndex, $(this).index());
    });

  });
})(jQuery);
Руслан

Привет не подскажете? использую последний код для активации таба после перехода по ссылке с якорем но активируется только 2 таб, не могу понять в чем проблема

Попробуйте такой HTML:

<ul class='tabs__caption'>
  <li class='active'><a href='#tab1'>1-я вкладка</a></li>
  <li><a href='#tab2'>2-я вкладка</a></li>
  <li><a href='#tab3'>3-я вкладка</a></li>
</ul>

и такой JS:

(function($) {
  $(function() {

    $('ul.tabs__caption').on('click', 'li:not(.active)', function() {
      $(this)
      .addClass('active').siblings().removeClass('active')
      .closest('div.tabs').find('div.tabs__content').removeClass('active').eq($(this).index()).addClass('active');
    });

    var tabIndex = window.location.hash.replace('#tab','')-1;
    if (tabIndex != -1) $('ul.tabs__caption li').eq(tabIndex).click();

  });
})(jQuery);

Я проверил, вроде бы работает.

Здравствуйте.
Спасибо за материал.
Подскажите, пожалуйста, как дополнительно сделать, чтобы при переходе по ссылке несколько элементов с табами переключались?
Чтобы понятнее было: у меня 5 блоков, в каждом по 3 вкладки. Над ними 3 кнопки. Необходимо, чтобы по нажатию кнопки 1-3, раскрывались табы 1-3.
Вариант с якорем, к сожалению, раскрывает только 1ый элемент.

Почемуто Четвертая вкладка через букву р(Червертая ) :) самое смешное что по ссылке оригинала тоже самое:)

Ну я не писал этот код с нуля) Спасибо за замечание, исправил.

Георгий

только я хотел позаимствовать ваш вариант табов, но… в мобильной версии, когда из-за маленькой ширины экрана закладки встают друг над другом, чтобы выбрать таб, надо нажимать на 50px ниже, чем его закладка находится :) садитесь, два =(

1. Скрипт рабочий.
2. Стили для мобильного вы можете написать любые.
3. В примере стили и скрипты упрощены до минимума, чтобы понять логику скрипта.

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

Степан

Спасибо за самый рабочий и минималистичный пример!
Но вот такой вопрос: А можно ли при 3-4 вкладках сделать некоторые из них неактивные?

Это как?.. Можно подробнее?

Степан

Прошу прощения за столь долгий ответ. Проблему я уже решил.
Например, на сайте всегда присутствует несколько разделов (3-4), но на определенных страницах некоторые из разделов не имеют информации, и эти разделы необходимо скрыть, не скрывая кнопки. Решение простое — сделать неактивными сами кнопки (спокойно делается через CSS).
Но вот другой вопрос: на странице есть заголовки, на которые можно перейти в меню разделов. За меню и заголовками закреплены определенные id.

Заголовки:
<h2><a id="A">A</a></h2>
<h2><a id="B">B</a></h2>
<h2><a id="C">C</a></h2>
<h2><a id="D">D</a></h2>
...
Меню:
<a href="#A">A</a>
<a href="#B">B</a>
<a href="#C">C</a>
<a href="#D">D</a>
...

Также на этой странице присутствует несколько вкладок. Как сделать, чтобы меню тоже менялось при смене вкладок?
Просто заметил особенность — скрипты и даже стандартные переходы по разделам не работают уже на 2 вкладке. На 1 все в порядке.

Добавьте пример на codepen.io — там будет понятнее, какие блоки существуют и как они выглядят, что должно происходить.

Степан

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

Загвоздка в том, что в моем случае вкладки используются для, практически, одного и того же контента, за исключением некоторых блоков. В пример можно привести сайт с полезным советом для установки чего-либо. Один раздел отводится для Windows, другой для MacOS — чтобы пользователь знал, как действовать на любой из систем. Основные шаги одинаковые, но пути и некоторые действия различаются.

И почему-то никакие скрипты, работающие на 1 вкладке, не хотят работать ни на 2, ни на любой другой вкладке. Поэтому я подумал про смену контента в меню разделов, чтобы заменить id (ведь, скорее всего, для продублированного контента невозможно применить один и тот же скрипт). К слову, в моем проекте контент находится в теге article, а меню разделов — в теге aside.
Поэтому повторю вопрос: как сделать смену контента не только для основного блока, но и какого-нибудь другого на странице?

P.S.
Пока писал, нашел решение для смены меню разделов каждой вкладки. Просто меню вставить внутрь контента, немного поменяв стили… Но проблема с нерабочими скриптами на других вкладках остается актуальной.

Интересно посмотреть на живой пример.

Получил пример на почту.

1. На всей странице не должно быть одинаковых id — они уникальны и у каждого элемента должен быть свой id — это важно, из-за это и не работало меню.

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

3. Более правильно будет вынести правое меню внутрь каждого таба со своими id и своими ссылками для этих id.

4. Не совсем правильно, но чуть проще по верстке и чуть сложнее по скриптам я выслал код на почту. Там меню боковое остается одно, но при разных активных табах в этом меню подменяются ссылки для каждого активного Таба со своими уникальными ID.

Руслан

Здравствуйте, спасибо большое за пример, сделал на его основе показ скриншотов, а думал городить какой-то скрипт слайдера. Не подскажите, можно как-то реализовать автоматическое переключение спустя какое-то время?
Например, переключение вкладок через 1 секунду. Спасибо!

Верстальщик

Здравствуйте! Подскажите, пожалуйста, можно ли сделать переключение вкладок через поле ?

1-я вкладка
2-я вкладка

Ответить