JustSneaker
@JustSneaker
Front-end разработчик

Как реализовать моргающую лампу?

Привет.
В DOM есть объект - лампа. Она состоит из png лампы и png её света. Нужно сделать асинхронную реализацию так, чтобы этот свет исчезал на доли секунды каждый "рандомный" момент времени (от 1 до 3 секунд). setInterval с Math.random() работает криво, и получается, что лампа сначала очень быстро моргает, потом свет появляется и перестаёт исчезать.

Если интересно, я делаю вот так:
var numInterval = setInterval(lampSwitch, Math.floor(Math.random(1, 3)) * 1000);

function lampSwitch() {
	$('.lampShadow').css({
		'display': 'none'
	});
	setTimeout(function() {
		$('.lampShadow').css({
			'display': 'block'
		});
	}, 600)
};
  • Вопрос задан
  • 809 просмотров
Решения вопроса 1
Stalker_RED
@Stalker_RED
Главная ошибка у вас в первой строке.
Выражение Math.floor(Math.random(1, 3)) * 1000 вычисляется один раз при запуске, и потом только с этим интервалом и работает.

Я бы делал немножко по другому: несколько флагов, которые переключаются независимыми таймерами, через 300, 500, 700 миллисекунд, например (основано на ряде простых чисел).

Когда все три флага совпали - моргаем лампочкой. Такие таймеры дадут довольно длинную псевдослучайную последовательность без очевидных шаблонных повторений.
(function(){
	var a = b = c = true, lamp = document.querySelector('.lamp')
  setInterval(function(){
    if (a && b && c) {
      lamp.classList.add('off')
      setTimeout(function(){
        lamp.classList.remove('off')
      }, 40) // это три кадра при 60 fps
    }
  }, 200)
  
  setInterval(function(){ a = !a }, 300)
  setInterval(function(){ b = !b }, 500)
  setInterval(function(){ c = !c }, 700)
})()
числа в таймерах можно подправить на свой вкус
https://jsfiddle.net/wo78t98z/

UPD: Вариант на css
У враппера желтый фон, поверх два прозрачных псевдоэлемента и пнг-шка с лампочкой.
У псевдоэлементов и пнг-шки независимые таймеры, которые кратковременно моргают черным.
.lamp::before,
.lamp::after {
  background: transparent;
  animation: blink 7.5s step-start infinite;
}
.lamp::after {
  animation-duration: 13s;
}
.lamp img {
  animation: blink 3s step-start infinite;
}

@keyframes blink {
  0%, 1% { background: #000; }
  100% { background: transparent; }
}
https://jsfiddle.net/wo78t98z/1/
Ответ написан
Пригласить эксперта
Ответы на вопрос 1
как вариант рекурсию сделать в вашей же функции lampSwitch
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы