用途:JS是单线程语言,一些复杂的计算,可能会影响主线程的运行,造成堵塞,导致页面无法及时绘制,进而出现卡顿、短暂白屏现象等。为此,使用new Worker可以创建额外的线程来解决复杂的计算,计算完结果后再返回给主线程,从而提升性能。(注意不能操作dom元素)
1、创建文件夹workers,创建demo_worker.ts文件(代表1个线程)
文件路径src\workers\demo_worker.ts
// self,可以理解为当前线程实例对象
// onmessage 监听主线程是否有发送消息过来
self.onmessage = (e) => {
console.log('主线程发送过来的数据', e.data)
const { data } = e
data.name = '小猪' //修改数据
self.postMessage(data) //发送修改完后的数据给主线程
}
2、主线程上使用(即Vue组件文件)
文件路径src\views\Workers.vue
<template>
<p>{{ workderData.name }}</p>
<el-button @click="startWorker">开始工作</el-button>
<el-button @click="stopWorker">停止工作</el-button>
</template>
<script setup lang="ts">
// vite 特有引入方式?worker
// vite官网原话:一个 web worker 脚本可以直接通过添加一个 ?worker 或 ?sharedworker 查询参数来导入。
// 默认导出一个自定义的 worker 构造器:
// import MyWorker from './worker?worker'
// const worker = new MyWorker()
import Worker from "@/workers/demo_worker?worker"
import { ref } from "vue"
const workderData = ref({
name: '佩奇',
age: 26
})
type W = InstanceType<typeof Worker>
let worker: W | null = null
const startWorker = () => {
worker = new Worker() //创建线程实例对象
worker.postMessage(JSON.parse(JSON.stringify(workderData.value))) //主线程发送数据给线程
// 监听线程数据处理结果
worker.onmessage = e => {
console.log('线程完成', e)
workderData.value = e.data
}
}
const stopWorker = () => {
(worker as W).terminate() //停止线程工作
}
</script>
<style scoped></style>
3、浏览器基本上都支持
Internet Explorer 10, Firefox, Chrome, Safari 和 Opera 都支持Web workers.
4、检测浏览器是否支持 Web Worker(实际项目可以不考虑,除非IE浏览器)
if (typeof (Worker) !== "undefined") {
// 是的! Web worker 支持!
// 一些代码.....
} else {
//抱歉! Web Worker 不支持
}