我继续我的画布爱好aa-在尝试用网络工作者卸载大部分事情时遇到了另一个问题。这是当前的设计:[从 index.html 创建和启动核心 web worker core.js]
var canvas = document.getElementById('testcanvas');
canvas.imageSmoothingEnabled = false;
const offscreenCanvas = canvas.transferControlToOffscreen();
const core = new Worker('core.js');
//transfer offscreenCanvas just ONCE or will get a 'An OffscreenCanvas could not be cloned because it was detached' error
core.postMessage({canvas: offscreenCanvas, msg: 'start'}, [offscreenCanvas]);
[在 core.js 中我创建了两个网络工作者]
'use strict'; //meh
const render = new Worker('render.js');
const mainloop = new Worker('mainloop.js');
onmessage = function(ev) {
if (ev.data.msg === 'start') {
mainloop.postMessage({msg: 'start'});
}
if (ev.data.canvas) {
render.postMessage({canvas: ev.data.canvas}, [ev.data.canvas]);
}
if (ev.data.posX && ev.data.posY) {
render.postMessage({posX: ev.data.posX, posY: ev.data.posY});
}
}
每个网络工作者将结果发送给核心工作者 [mainloop.js]
'use strict';
var canvas;
var ctx;
var speed = 100;
var currentTime = 0; var timeDiff = 0; var lastTime = 0;
var timeProduct = 0; var dTime = 0; var timeScale = 1; var timeStep = 0.01;
var posX = 10; var posY = 10;
function main() {
currentTime = performance.now();
timeDiff = (Math.abs(currentTime - lastTime) * 0.001);
dTime += Math.min(timeDiff, 1);
timeProduct = timeStep * timeScale;
while (dTime > timeProduct) {
postMessage({posX: posX, posY: posY});
dTime -= timeProduct;
}
lastTime = currentTime;
posX += speed * timeDiff;
posY += speed * timeDiff;
if (posX > 500) posX = 10;
if (posY > 500) posY = 10;
requestAnimationFrame(main);
//setTimeout(main, 0);
}
onmessage = function(ev) {
if(ev.data.msg === 'start') {
main();
}
}
[渲染.js]
'use strict';
var canvas;
var ctx;
function draw(posX, posY) {
//clear
ctx.setTransform(1,0,0,1,0,0);
ctx.clearRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = "#000000";
ctx.fillRect(0, 0, canvas.width, canvas.height);
//draw
ctx.beginPath();
ctx.moveTo(posX, posY);
ctx.ellipse(posX,
posY,
5,
5,
0.7854,
0,
2 * Math.PI,
false);
ctx.strokeStyle = "white";
ctx.stroke();
}
onmessage = function(ev) {
if(ev.data) {
if (!canvas) canvas = ev.data.canvas;
if (!ctx) ctx = canvas.getContext('2d');
draw(ev.data.posX, ev.data.posY);
}
}
问题是,当requestAnimationFrame(main)
在 mainloop.js 中调用时,我收到“此 Worker 不支持的 requestAnimationFrame”,尽管offscreenCanvas
已在核心和渲染工作者之间转移。当更改setTimeout(main, 0)
错误消失但没有在画布上绘制...