Почему рисование на холсте асинхронно, а API синхронно? - PullRequest
0 голосов
/ 11 июня 2019

Я пишу визуализацию нейронной сети, и я хотел бы перерисовывать ее на каждой итерации обучения, поэтому у меня есть следующая кнопка с обратным вызовом onclick:

startButton.onclick = () => {
  for (let i = 0; i < trainData.length; i++) {
    setTimeout(() => {
      network.trainSample(trainData[i])
      ctx.clearRect(0, 0, width, height)
      drawNN(network)
    }, 0)
  }
}

Проблема в том, что если я сниму setTimeout, он выполнит все тренировки и перерисовает все в конце.

Насколько я знаю, есть цикл обработки событий и, что делает трюк setTimeout, он создает задание в очереди событий, которое будет выполнено не точно сейчас, а как можно скорее .

Хорошо, но если рисование на холсте асинхронно и рисование get откладывается до конца, почему его API синхронен?

Минимальный пример:

const canv = document.getElementById('myCanv')
const ctx = canv.getContext('2d')

ctx.strokeStyle = '#000000'

for (let x = 0; x <= 100; x++) {
  ctx.clearRect(0, 0, 100, 100)
  ctx.beginPath()
  ctx.moveTo(0, 0)
  ctx.lineTo(x, 100)
  ctx.stroke()
}
<!DOCTYPE html>
<html>

<head>
</head>

<body>
  <canvas width="100" height="100" id="myCanv"></canvas>
</body>

</html>

1 Ответ

1 голос
/ 11 июня 2019

Вы используете неправильно, и даже если рисование на холсте было синхронным, вы, скорее всего, все равно увидели бы только последний кадр с какой-то слишком быстрой странной анимацией между ними.Вам нужно вместо стандартного цикла использовать какой-то цикл анимации.Например:

let i = 0;
function animationLoop() {
  if (i < trainData.length) {
     network.trainSample(trainData[i]);
     ctx.clearRect(0, 0, width, height);
     drawNN(network);
     i++;
     requestAnimationFrame(animationLoop);
  }
}
requestAnimationFrame(animationLoop);

Здесь я использую requestAnimationFrame, что дает около 60 кадров в секунду.Я думаю, для вашего случая это все еще может быть слишком быстро.Вы можете ограничить количество кадров в секунду, используя дополнительную setTimeout функцию animateLoop.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...