Включить CSS автозапуск слайд-шоу с JavaScript - PullRequest
1 голос
/ 12 марта 2020

Я сделал простое слайд-шоу, используя только CSS, где при щелчке переключателя поле элемента изменяется, чтобы отобразить нужный слайд. Вы можете увидеть, как это работает, во фрагменте кода ниже. Я также сделал автоматическое воспроизведение этого слайд-шоу с JavaScript. Скрипт проверяет следующую радиокнопку в списке каждые 3 секунды.

Теперь мне нужна помощь для автоматического воспроизведения слайд-шоу в oop, а также для остановки автоматического воспроизведения когда вы проверяете любую радиокнопку вручную .

$(document).ready(function() {

  function autoplay() {
$("input[name=radio-button]:checked").nextAll(':radio:first').prop('checked', true);
  };
  
  setInterval(autoplay, 3000);

});
body {
margin: 0;
padding: 0;
}

.slider {
  width: 300%;
  transition: margin 1s;
  height: 100px;
}

#radio-button1:checked ~ .slider {
  margin-left: 0%;
}

#radio-button2:checked ~ .slider {
  margin-left: -100%;
}

#radio-button3:checked ~ .slider {
  margin-left: -200%;
}

.slider-item {
  float: left;
  width: 33.33%;
  height: 100%;
}
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<input type="radio" name="radio-button" id="radio-button1" checked />
<input type="radio" name="radio-button" id="radio-button2" />
<input type="radio" name="radio-button" id="radio-button3" />

<div class="slider">
  <div class="slider-item" style="background: #F00"></div>
  <div class="slider-item" style="background: #0F0"></div>
  <div class="slider-item" style="background: #00F"></div>
</div>

Ответы [ 2 ]

3 голосов
/ 12 марта 2020

Создайте переменную curr, увеличьте ее внутри интервала и используйте по модулю % до l oop значение обратно до 0:

jQuery(function($) { // DOM ready and $ alias in scope

  var curr = 0;

  function autoplay() {
    curr = ++curr % 3; // Increment and Reset to 0 when 3
    $("[name=radio-button]")[curr].checked = true;
  }

  setInterval(autoplay, 3000);

});
body {
  margin: 0;
  padding: 0;
}

.slider {
  width: 300%;
  transition: margin 1s;
  height: 100px;
}

#radio-button1:checked~.slider {
  margin-left: 0%;
}

#radio-button2:checked~.slider {
  margin-left: -100%;
}

#radio-button3:checked~.slider {
  margin-left: -200%;
}

.slider-item {
  float: left;
  width: 33.33%;
  height: 100%;
}
<input type="radio" name="radio-button" id="radio-button1" checked />
<input type="radio" name="radio-button" id="radio-button2" />
<input type="radio" name="radio-button" id="radio-button3" />

<div class="slider">
  <div class="slider-item" style="background: #F00"></div>
  <div class="slider-item" style="background: #0F0"></div>
  <div class="slider-item" style="background: #00F"></div>
</div>

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

Лучший способ:

  • Переполнить супер-родитель, чтобы вы не получили полосы прокрутки
  • Используйте display: flex; вместо некрасивых float.
  • Используйте $('.slider').each(, чтобы вы могли иметь несколько ползунков на одной странице!
  • Создайте функции anim() play() и stop() для управления происходящим.
  • Анимируйте, используя transform: и transition, поскольку переход ускоряется с помощью графического процессора. В то время как поля не являются, и требуют перекраски и перекраски.
  • Анимируйте преобразование с помощью curr * -100%
  • . Используйте curr %= tot (оператор по модулю), чтобы при необходимости возвратить индекс curr в 0.
  • Зачем создавать кнопки вручную? Создайте свои слайды вручную и позвольте JS создать кнопки для вас.
  • Используйте setInterval, сохраняя его в переменной itv
  • Чтобы остановить автоматическую анимацию, используйте clearInterval(itv)
  • Используйте .hover(stop, play) для остановки при вводе мыши и автовоспроизведение при отпускании мыши

$('.slider').each(function(slider_idx) { // Use each, so you can have multiple sliders

  let curr = 0;             // Set current index
  let itv = null;           // The interval holder
  
  const $slider = $(this);
  const $nav    = $('.slider-nav', $slider);
  const $items  = $('.slider-items', $slider);
  const $item   = $('.slider-item', $slider);
  const tot = $item.length; // How many
  const btns = [...new Array(tot)].map((_, i) => $('<input>', {
    type: 'radio',
    name: `slider-btn-${slider_idx}`,
    checked: curr == i,
    change() { // On button change event
      curr = i; // Set current index to this button index
      anim();
    }
  })[0]);
    
  function anim() {
    $items.css({transform: `translateX(-${curr*100}%)`}); // Animate
    btns[curr].checked = true; // Change nav btn state
  }

  function play() {
    itv = setInterval(() => {
      curr = ++curr % tot; // increment curr and reset to 0 if exceeds tot
      anim(); // and animate!
    }, 3000); // Do every 3sec
  }
  
  function stop() {
    clearInterval(itv);
  }

  $nav.empty().append(btns);   // Insert buttons
  $slider.hover(stop, play);   // Handle hover state
  play();                      // Start autoplay!

});
/*QuickReset*/ * {margin: 0; box-sizing: border-box;}

.slider {
  position: relative;
  height: 100px;
}

.slider-overflow {
  overflow: hidden; /* use an overflow parent! You don't want scrollbars */
  height: inherit;
}

.slider-items {
  display: flex; /* Use flex */
  flex-flow: row nowrap;
  height: inherit;
  transition: transform 1s; /* Don't use margin, use transform */
}

.slider-item {
  flex: 0 0 100%;
  height: inherit;
}

.slider-nav {
  position: absolute;
  width: 100%;
  bottom: 0;
  text-align: center;
}
<div class="slider">

  <div class="slider-overflow">
    <div class="slider-items"> <!-- This one will transition -->
      <div class="slider-item" style="background:#0bf;">curr = 0</div>
      <div class="slider-item" style="background:#fb0;">curr = 1</div>
      <div class="slider-item" style="background:#f0b;">curr = 2</div>
    </div>
  </div>
  
  <div class="slider-nav">
    <!-- JS will populate buttons here -->
  </div>
  
</div>

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

Таким образом, оба элемента DIV .slider-nav и .slider-overflow должны быть внутри общего родителя .slider - чтобы мы правильно остановились ( пауза) авто-анимация после любого взаимодействия с этими элементами.

2 голосов
/ 13 марта 2020

Зацикливание слайд-шоу

Чтобы l oop слайд-шоу, вам нужно изменить функцию autoplay на:

  • Получить список всех переключателей,
  • Определите, какая из них отмечена,
  • Снимите отметку и отметьте следующую в списке,
    • Уделяя особое внимание переносу на первую один, если уже в конце.

Я переименую функцию next.

function next() {
  // get all the radio buttons.
  var buttons = $('input[name="radio-button"]');

  // look at each one in the list.
  for (let i = 0; i < buttons.length; i++) {

    // if this one isn't the checked one, move on to the next.
    if (!buttons[i].checked) {
      continue;
    }

    // okay, so this one is checked. let's uncheck it.
    buttons[i].checked = false;

    // was this one at the end of the list?
    if (i == buttons.length - 1) {
      // if so, the new checked one should be the first one.
      buttons[0].checked = true;
    } else {
      // otherwise, just the new checked one is the next in the list.
      buttons[i + 1].checked = true;
    }

    // now that we've made that change, we can break out of the loop.
    break;
  }
}

В качестве бонуса вы можете легко сделать аналогичная функция называется от prev до go в обратном направлении.

Остановка слайд-шоу

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

Функция .setInterval() возвращает «идентификатор интервала». Этот идентификатор может быть использован для внесения изменений в интервал позже - например, его остановка.

var timer = setInterval(next, 3000);

Затем, позже, вы захотите передать это значение timer обратно в clearInterval для остановки таймера.

clearInterval(timer);

Было бы проще разделить это на две функции, start и stop, и пусть значение timer будет глобальным:

var timer;

function start() {
  timer = setInterval(next, 3000);
}

function stop() {
  clearInterval(timer);
}

Теперь вы можете вызывать функцию stop всякий раз, когда любая из переключателей получает событие click:

$('input[name="radio-button"]').on('click', stop);

Полный пример

Это ваш код с модификациями, описанными выше.

Я добавил кнопки «Пуск», «Стоп», «Предыдущая» и «Далее» - они не нужны для функция. Они просто для демонстрационных целей.

$(document).ready(function() {
  /* the list of buttons is not dynamic, so rather than fetching the list of
   * buttons every time `next` or `prev` gets executed, we can just fetch it
   * once and store it globally. */
  var buttons = $('input[name="radio-button"]');
  var timer;
  
  function start() {
    timer = setInterval(next, 3000);
  }
  
  function stop() {
    clearInterval(timer);
  }

  function next() {
    for (let i = 0; i < buttons.length; i++) {
      if (!buttons[i].checked) {
        continue;
      }
      buttons[i].checked = false;
      if (i == buttons.length - 1) {
        buttons[0].checked = true;
      } else {
        buttons[i + 1].checked = true;
      }
      break;
    }
  }
  
  function prev() {
    for (let i = 0; i < buttons.length; i++) {
      if (!buttons[i].checked) {
        continue;
      }
      buttons[i].checked = false;
      if (i == 0) {
        buttons[buttons.length - 1].checked = true;
      } else {
        buttons[i - 1].checked = true;
      }
      break;
    }
  }
  
  start();
  
  buttons.on('click', stop);
  
  /* these next lines are unnecessary if you aren't including the buttons */
  $('#start').on('click', start);
  $('#stop').on('click', stop);
  $('#next').on('click', next);
  $('#prev').on('click', prev);
});
body {
  margin: 0;
  padding: 0;
}

.slider {
  width: 300%;
  transition: margin 1s;
  height: 100px;
}

#radio-button1:checked~.slider {
  margin-left: 0%;
}

#radio-button2:checked~.slider {
  margin-left: -100%;
}

#radio-button3:checked~.slider {
  margin-left: -200%;
}

.slider-item {
  float: left;
  width: 33.33%;
  height: 100%;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<input type="radio" name="radio-button" id="radio-button1" checked />
<input type="radio" name="radio-button" id="radio-button2" />
<input type="radio" name="radio-button" id="radio-button3" />

<div class="slider">
  <div class="slider-item" style="background: #F00"></div>
  <div class="slider-item" style="background: #0F0"></div>
  <div class="slider-item" style="background: #00F"></div>
</div>

<!-- these buttons are unnecessary, they are only for demonstration purposes -->
<button id="start">Start</button>
<button id="stop">Stop</button>
<button id="prev">Prev</button>
<button id="next">Next</button>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...