I have a ul with some
li
li
.active
.active
li
li
<ul>
<li class="light active"></li>
<li class="light"></li>
<li class="light"></li>
<li class="light"></li>
<li class="light"></li>
</ul>
(function() {
var lights = document.getElementsByClassName("light");
var random = Math.floor(Math.random() * (lights.length - 1)) + 0;
var randomLight = lights[random];
function repeatOften() {
randomLight.classList += randomLight.classList ? ' active' : ' light';
requestAnimationFrame(repeatOften);
}
requestAnimationFrame(repeatOften);
})();
The right choice to run a function in a more-or-less known time in the future is setTimeout
. requestAnimationFrame
is meant for something that should run as often as is feasible without interrupting the render loop, say 60 times a second (aka "at 60 fps").
In your case you have a relatively slow update rate of once a second, so setTimeout
isn't hurting.
You probably want to keep track of two elements: The one you're changing and the one you previously changed, so you can reset it.
Also, classList.toggle
comes in handy as it adds or removes a class, based on if it's already present or not.
(function() {
var lights = document.getElementsByClassName("light");
var previousLight = null;
function repeatOften() {
if (previousLight) previousLight.classList.toggle('active')
var random = Math.floor(Math.random() * (lights.length - 1)) + 0;
var randomLight = lights[random];
randomLight.classList.toggle(randomLight);
previousLight = randomLight;
setTimeout(repeatOften, 1000);
}
setTimeout(repeatOften, 1000);
})();
Here is the updated (and slightly changed) pen.