canvas是否有显示事件处理程序?

时间:2014-10-11 22:51:36

标签: javascript html5 canvas webgl

我习惯使用GLUT的PostRedisplay和(App | UI)工具包的setNeedsDisplay方法来请求新的显示事件应用程序希望重绘场景时发布到事件队列。我还没有找到与HTML5的Canvas元素相对应的内容。例如,当我想重绘到画布时,我目前只是直接调用我的display()函数:

function mouseMove(event) {
      if (mouseDrag) {
          // update camera position
          display();
      }
  }

display()函数渲染场景(可能很昂贵):

function display() {
      gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
      // issue WebGL calls to redraw scene
      gl.flush();
}

如果在上次渲染完成之前发生多个渲染请求,我习惯使用的大多数系统会将多个显示事件合并为一个事件。如果长display()次调用超过渲染速度,我上面所做的事情可能会有问题。

无论如何,有效重绘画布元素的正确方法是什么?

You can see the demo app I am working on here(如果您启用了WebGL)。

更新:根据以下答案,我现在使用RequestAnimationFrame并使用返回值作为标志来指示已经发出请求。渲染场景时,我清除了标志,因此可以进一步请求:

var requestId = 0; // id of current requestAnimationFrame request (0 = no request)

function mouseMove(event) {
      if (mouseDrag) {
          // update camera position
          if (requestId)
            requestId = requestAnimationFrame(display);
          else
             console.log("request already in queued"); // test
      }
 }

function display() {
      requestId = 0;
      // redraw scene
}

注意到我收到的日志消息确实合并了多个请求。这似乎是一个很好的方法。还有其他解决方案吗?

1 个答案:

答案 0 :(得分:2)

您可以使用requestAnimationFrame(display)设置回调(在这种情况下,display),以便在下次重绘时调用。

在等待重新绘制时,您只能调用一次(在重新绘制时,它将执行回复您对requestAnimationFrame进行的每次调用) 。如果您想要连续制作动画,还可以请求另一个动画帧。