mousemove/keypress时重置倒计时计时器及弹窗重复问题求助
问题解决:倒计时重置时多次弹出alert的修复
问题说明
需要实现鼠标移动(mousemove)或按键(keypress)时,将倒计时计时器重置为初始时间。当前脚本已添加重置功能,但触发这些事件时,alert('times up')会多次弹出,需要解决该问题。
问题根源
- 定时器变量作用域错误:原代码中
var x = setInterval(...)是countdown函数的局部变量,resetTimer里的clearInterval(x)无法访问到这个局部变量,导致旧的定时器没有被真正清除,每次重置都会新建一个定时器,多个定时器同时运行,到时间后每个都会触发timeup函数,造成多次alert。 mousemove事件触发过于频繁:鼠标移动时会连续触发大量mousemove事件,每次都调用resetTimer,短时间内创建大量未被清除的定时器,进一步加剧了重复alert的问题。
修复方案
- 将定时器变量
x声明为全局变量,确保resetTimer能正确清除当前运行的定时器。 - 给
mousemove事件添加防抖处理,避免短时间内重复触发重置逻辑。 - 在
countdown函数中先清除已有定时器,防止意外创建多个定时器。
修复后的代码
JavaScript 代码
// 全局变量存储定时器实例 let x = null; // 防抖定时器,用于控制mousemove触发频率 let debounceTimer = null; jQuery(document).ready(function () { // mousemove添加防抖,300ms内只执行一次resetTimer $(this).mousemove(function() { clearTimeout(debounceTimer); debounceTimer = setTimeout(resetTimer, 300); }); $(this).keypress(resetTimer); }); function resetTimer() { // 清除当前运行的定时器 if (x) clearInterval(x); countdown(); } function countdown() { // 再次确保清除定时器,避免重复创建 if (x) clearInterval(x); // 设置倒计时时间(这里是10分钟:1000*60*10) const countDownDate = Date.now() + 1000 * 60 * 10; // 更新倒计时,每秒执行一次 x = setInterval(function() { const now = Date.now(); const distance = countDownDate - now; // 计算分秒 const minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60)); const seconds = Math.floor((distance % (1000 * 60)) / 1000); // 格式化秒数,小于10时补0 const formattedSeconds = seconds.toString().padStart(2, '0'); document.getElementById("SessionCookieExpirationCountdown").innerHTML = `Logging out in ${minutes}:${formattedSeconds}`; // 倒计时结束处理 if (distance < 0) { clearInterval(x); document.getElementById("SessionCookieExpirationCountdown").innerHTML = "Countdown End"; timeup(); } }, 1000); } function timeup() { alert('times up'); }
HTML 代码
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <body onload="countdown()"> <div id="SessionCookieExpirationCountdown"></div> </body>
关键修复点说明
- 全局定时器变量:将
x设为全局变量,确保resetTimer能精准清除当前运行的定时器,避免多个定时器同时存在。 - 防抖处理:对
mousemove事件添加300ms防抖,避免鼠标移动时连续触发重置,减少不必要的定时器创建和销毁。 - 双重清除定时器:在
resetTimer和countdown开头都检查并清除定时器,确保不会出现漏清的情况。
内容的提问来源于stack exchange,提问作者Jan Bantolinay
相关产品推荐
相关产品推荐

