【问题标题】:HTML canvas double buffering frame-rate issuesHTML画布双缓冲帧率问题
【发布时间】:2011-05-31 04:27:16
【问题描述】:

我有一个全屏画布,上面绘制了 3 张图像。当我调整窗口大小时,这些图像会改变位置;但是,它似乎非常有问题,在 Firefox 中更是如此。

我一直在阅读双缓冲应该可以解决此问题,但我想知道在下一个位置未知时如何进行双缓冲。也就是说,我无法确定以后应该缓冲什么,这怎么可能呢?

这是一个似乎可行的来源,但我不完全理解 Fedor 试图解释的概念。

Does HTML5/Canvas Support Double Buffering?

到目前为止,

    $canvas = $('#myclouds')[0];
    $canvas_buffer = $('canvas')[0].insertAfter($canvas).css('visibility', 'hidden');
    context = $canvas.getContext('2d');
    context_buffer = $canvas_buffer.getContext('2d');
    clouds_arr = [$canvas, $canvas_buffer];

$(window).resize(function () {
    drawCanvas();
};

function initCanvas() {

    // Sources for cloud images
    var cloud1 = '/js/application/home/images/cloud1.png',
        cloud2 = '/js/application/home/images/cloud2.png',
        cloud3 = '/js/application/home/images/cloud3.png';

    // add clouds to be drawn
    // parameters are as follows:
    // image source, x, y, ratio, adjustment)
    addCloud(cloud1, null, 125, .03);
    addCloud(cloud2, null, 75, .15);
    addCloud(cloud3, null, 50, .55);
    addCloud(cloud1, null, 125, .97, 300);
    addCloud(cloud2, null, 70, .85, 300);
    addCloud(cloud3, null, 45, .5, 300);

    // Draw the canvas
    drawCanvas();
}

function drawCanvas() {
    // Reset
    $canvas.attr('height', $window.height()).attr('width', $window.width());

    // draw the clouds
    var l = clouds.length;
    for (var i = 0; i < l; i++) {
        clouds[i].x = ($window.width() * clouds[i].ratio) - clouds[i].offset;
        drawimage(context, clouds[i]);
    }
}

function Cloud() {
    this.x = 0;
    this.y = 0;
}

function addCloud(path, x, y, ratio, offset) {
    var c = new Cloud;
    c.x = x;
    c.y = y;
    c.path = path;
    c.ratio = ratio || 0;
    c.offset = offset || 0;
    clouds.push(c);
}

function drawimage(ctx, image) {
    var clouds_obj = new Image();
    clouds_obj.src = image.path;

    clouds_obj.onload = function() {
        ctx.drawImage(clouds_obj, image.x, image.y);
    };
}

【问题讨论】:

    标签: javascript jquery canvas double-buffering


    【解决方案1】:

    我想你可能误解了什么是双缓冲。它是一种在显示器上平滑实时渲染图形的技术。

    这个概念是你有两个缓冲区。任何时候只有一个可见。当你去绘制构成框架的元素时,你将它们绘制到不可见的缓冲区中。在你的情况下,云。然后翻转缓冲区,使隐藏的缓冲区可见,而可见的缓冲区隐藏。然后在下一帧绘制到现在新隐藏的缓冲区。然后在绘制结束时翻转回来。

    这样做的目的是阻止用户在一帧完成之前看到元素的部分渲染。在游戏系统上,这也将与显示器的垂直刷新同步,以实现真正的平滑并防止出现撕裂等伪影。

    查看上面的代码,您似乎已经创建了两个画布元素,但您只使用了第一个 Context 对象。我认为这是不完整的,因为没有发生翻转。

    另外值得注意的是,窗口调整大小事件在拖动时会连续触发,这可能会导致疯狂的渲染。我通常在 resize 事件上创建一个计时器以实际重新渲染。这样,只有在用户停止调整大小几毫秒后才会重新渲染。

    此外,您的绘图例程每次都会创建新的 Image 对象,而您不需要这样做。您可以使用一个图像对象并多次渲染到画布。这将大大加快您的渲染速度。

    希望这会有所帮助。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-07-27
      • 1970-01-01
      • 2013-11-30
      • 2020-04-01
      • 2014-04-19
      • 1970-01-01
      • 2014-04-07
      • 2012-09-01
      相关资源
      最近更新 更多