弹框不影响定时器的继续执行
因为 js 为单线程语言,所以在一般情况下,当弹框出现时,定时器是必定会停止的,如以下实例
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>土狗一号</title>
</head>
<body>
<div></div>
<button>弹框</button>
<script>
var div = document.body.children[0]
var test = 100
// 简单的定时器,让倒数继续
setInterval(function (){
test -= 1
div.innerHTML = test
}, 1000)
var button = document.body.children[1]
button.onclick = function (){
alert("test")
}
</script>
</body>
</html>

为了做到弹出弹框也让递减继续,必须要在js中使用多线程
需使用H5中提供的Web Worker对象
什么是Web Worker?
当在 HTML 页面中执行脚本时,页面的状态是不可响应的,直到脚本已完成。
web worker 是运行在后台的 JavaScript,独立于其他脚本,不会影响页面的性能。您可以继续做任何愿意做的事情:点击、选取内容等等,而此时 web worker 在后台运行。
也就是说,我们可以使用 web worker 创建一个实例,通过这个实例调用外部 JS。
这个外部 JS 此时正运行在后台,即使主页面出现了弹框,也不会影响后台的进程。
接下来我们对上面的例子进行改写:
HTML:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>土狗一号</title>
</head>
<body>
<div></div>
<button>ss</button>
<script>
// 创建实例,括号内跟路径
var worker1 = new Worker('./test.js')
var div = document.body.children[0]
// 向 web worker 添加一个 "onmessage" 事件监听器
// 箭头函数获得的 e.data 为 js 文件中 self.postMessage()返回的值
worker1.onmessage = e => {
// 把 js 文件中拿到的值赋给 div
div.innerHTML = e.data
}
/*
* 上面的操作就是把 js 中拿到的值赋给 div
*/
var button = document.body.children[1]
button.onclick = function (){
alert("test")
}
// 在 HTML 关闭脚本
// worker1.terminate()
</script>
</body>
</html>
JS:
var test = 100
// 设置定时器,每过一秒执行一次
self.setInterval(function(){
test -= 1
// 将拿到的值传给 HTML 页面
self.postMessage(test)
// 如果 test 走到0则 Worker 关闭自身,也就是停止运行该文件
if(test == 0){
// 在 Worker 内部关闭自身,如想在 HTML 中关闭则需用其他方法
self.close()
}
}, 1000)
注:最好部署在服务器上进行此操作(IE 某些版本也可以)否则可能会出现以下错误

由于谷歌的安全机制,此操作会被当做跨域......不允许在本地直接运行
但此方法有个很大的缺点!!!
因为 JS 本为单线程语言,所以上述代码的执行效率并不高,甚至可以说是很低...
在运行上述案例的时候就会发现,当点开弹窗后,数字递减的显示是有卡顿的。
但如果把弹窗关闭,卡顿则会消失(递减的次数不会受卡顿影响)
因此,在选用本方法时,一定要考虑应用场景。

浙公网安备 33010602011771号