我有一种奇怪的错误,我很难搞清楚。首先,这里是代码:
const canvas = document.getElementById('canvas');
const canvasContainer = document.getElementById('canvas-container');
const ctx = canvas.getContext('2d');
function resizeCanvas() {
canvas.width = canvasContainer.clientWidth;
canvas.height = canvasContainer.clientHeight;
}
async function init() {
window.addEventListener('resize', resizeCanvas)
resizeCanvas();
window.requestAnimationFrame(draw);
let poly = [];
canvas.addEventListener('click', ev => {
let x = ev.clientX - canvas.offsetLeft;
let y = ev.clientY - canvas.offsetTop;
poly.push([x,y]);
})
window.addEventListener('keyup', ev => {
if(ev.key === 'Escape') {
poly.length = 0;
}
});
let mousePos = null;
canvas.addEventListener('mouseleave', ev => {
mousePos = null;
})
canvas.addEventListener('mousemove', ev => {
let x = ev.clientX - canvas.offsetLeft;
let y = ev.clientY - canvas.offsetTop;
mousePos = {x,y};
console.log(x,y);
})
function draw() {
// ctx.save();
ctx.fillStyle = '#ADD5F8';
ctx.fillRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = '#C38F4C';
if(poly.length >= 3) {
ctx.beginPath();
ctx.moveTo(...poly[0]);
for(let i=1; i<poly.length; ++i) {
ctx.lineTo(...poly[i]);
}
ctx.closePath();
ctx.fill();
}
if(poly.length && mousePos) {
ctx.beginPath();
ctx.moveTo(...poly[0]);
for(let i=1; i<poly.length; ++i) {
ctx.lineTo(...poly[i]);
}
if(mousePos) {
console.log(mousePos);
ctx.lineTo(mousePos.x, mousePos.y);
}
ctx.strokeStyle = '#ff0000';
ctx.stroke();
}
window.requestAnimationFrame(draw);
}
}
function createImage(path) {
return new Promise((resolve,reject) => {
const img = new Image();
img.onload = () => resolve(img);
img.onerror = err => reject(err);
img.src = path;
})
}
async function createPattern(path, repetition='repeat') {
// TODO: https://stackoverflow.com/a/21128933/65387
const img = await createImage(path);
return ctx.createPattern(img, repetition);
}
init();
// TODO: add physics https://github.com/shakiba/planck.js
&#13;
* {
box-sizing: border-box;
}
.toolbox {
width: 100px;
background-color: #535353;
}
.content {
overflow: hidden;
background-color: green;
flex: 1;
}
.main {
display: flex;
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
}
&#13;
<div class="main">
<div class="toolbox">toolbox</div>
<div id="canvas-container" class="content">
<canvas id="canvas"></canvas>
</div>
</div>
&#13;
有趣的是,它似乎在这个小提琴中工作得很好。但是当我在Electron下运行它时,this is what happens(gifv链接) - (请忽略光标在视频中有点偏离的事实 - 我的屏幕录像机搞砸了) - 但请注意,只需点击几下,最后一条红线就会搞砸。
当我移动鼠标时,mousemove处理程序中的console.log
会触发,并且它会记录正确的坐标。但是,我在mousePos
中使用的draw()
var会固定在某个位置,然后不再更新。
我在每次鼠标移动事件中都更新了相同的变量,我不明白这两个console.logs会有什么不同?
如果我这样记录,watch what happens
canvas.addEventListener('mousemove', ev => {
let x = ev.clientX - canvas.offsetLeft;
let y = ev.clientY - canvas.offsetTop;
mousePos = {x,y};
console.log('a',x,y);
})
function draw() {
if(mousePos) {
console.log('b', mousePos.x, mousePos.y);
}
&#34; B&#34;卡在{102,570},即使&#34; a&#34;不断更新。它是同一个变量!
答案 0 :(得分:1)
让我看到你的代码的第一件事就是主init
函数被定义为async
函数,但却没有等待。
我不确定没有async
的{{1}}函数的预期行为,但问题似乎发生在同一时间段之后。
这是一个有趣的问题,值得进一步研究。在spec (async function definitions)中有很多东西需要阅读,快速浏览并没有显示任何明显的原因。
修复很简单,从函数await
中移除async
令牌,一切正常。
更改
init
到
async function init() {
function init() {
const canvas = document.getElementById('canvas');
const canvasContainer = document.getElementById('canvas-container');
const ctx = canvas.getContext('2d');
function resizeCanvas() {
canvas.width = canvasContainer.clientWidth;
canvas.height = canvasContainer.clientHeight;
}
function init() {
window.addEventListener('resize', resizeCanvas)
resizeCanvas();
window.requestAnimationFrame(draw);
let poly = [];
canvas.addEventListener('click', ev => {
let x = ev.clientX - canvas.offsetLeft;
let y = ev.clientY - canvas.offsetTop;
poly.push([x,y]);
})
window.addEventListener('keyup', ev => {
if(ev.key === 'Escape') {
poly.length = 0;
}
});
let mousePos = null;
canvas.addEventListener('mouseleave', ev => {
mousePos = null;
})
canvas.addEventListener('mousemove', ev => {
let x = ev.clientX - canvas.offsetLeft;
let y = ev.clientY - canvas.offsetTop;
mousePos = {x,y};
})
function draw() {
// ctx.save();
ctx.fillStyle = '#ADD5F8';
ctx.fillRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = '#C38F4C';
if(poly.length >= 3) {
ctx.beginPath();
ctx.moveTo(...poly[0]);
for(let i=1; i<poly.length; ++i) {
ctx.lineTo(...poly[i]);
}
ctx.closePath();
ctx.fill();
}
if(poly.length && mousePos) {
ctx.beginPath();
ctx.moveTo(...poly[0]);
for(let i=1; i<poly.length; ++i) {
ctx.lineTo(...poly[i]);
}
if(mousePos) {
ctx.lineTo(mousePos.x, mousePos.y);
}
ctx.strokeStyle = '#ff0000';
ctx.stroke();
}
window.requestAnimationFrame(draw);
}
}
function createImage(path) {
return new Promise((resolve,reject) => {
const img = new Image();
img.onload = () => resolve(img);
img.onerror = err => reject(err);
img.src = path;
})
}
async function createPattern(path, repetition='repeat') {
// TODO: https://stackoverflow.com/a/21128933/65387
const img = await createImage(path);
return ctx.createPattern(img, repetition);
}
init();
// TODO: add physics https://github.com/shakiba/planck.js
* {
box-sizing: border-box;
}
.toolbox {
width: 100px;
background-color: #535353;
}
.content {
overflow: hidden;
background-color: green;
flex: 1;
}
.main {
display: flex;
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
}