JS秒表多次启停后计时加速问题排查求助
秒表启停后加速的问题原因及修复方案
问题核心原因
每次点击start按钮时,你在事件处理函数里用var setIntID重新声明了变量,这会创建一个局部变量,覆盖了全局的setIntID。导致全局的setIntID从未被赋值为最新的定时器ID,当点击stop按钮时,clearInterval(setIntID)相当于在清除一个无效的ID,之前创建的定时器根本没有被真正关闭。
多次启停后,页面中会存在多个同时运行的定时器,每个定时器都会执行watchFunction累加时间,最终导致计时速度越来越快。
修复方法
把start事件里的var setIntID改成直接赋值,不要用var重新声明,让全局的setIntID能正确保存每次的定时器ID:
let ms = 0; let secs = 0; let mins =0; let flag = true; var setIntID; watchFunction =()=> { if(flag){ ms +=4 ; document.getElementById('msecs').innerText = `${ms}`; if(ms == 1000){ ms =0; secs++ document.getElementById('secs').innerText = `${secs}:` if(secs == 60){ mins++; document.getElementById('min').innerText = `${mins}:`; secs = 0; } }}} document.getElementById("start").addEventListener('click', function(){ flag = true; // 去掉var,直接给全局变量赋值 setIntID = setInterval(watchFunction,1); console.log(flag) //tracker }) document.getElementById("stop").addEventListener('click', function(){ flag = false; console.log(flag); //tracker clearInterval(setIntID); })
额外优化建议
- 浏览器中定时器的最小实际执行间隔约为4ms,
setInterval(watchFunction,1)无法达到1ms的精度,固定累加4的方式也不够准确,后续可以通过时间戳计算真实流逝的时间来更新计时,会更精准。 - 可以在start按钮点击时先判断是否已有运行中的定时器,避免重复点击start直接创建多个定时器。
内容的提问来源于stack exchange,提问作者John117
相关产品推荐
相关产品推荐

