Сдвинуть содержимое холста влево

Есть ли простой способ сдвинуть содержимое холста влево, отбрасывая крайние левые пиксели и перемещая все остальные влево?

Ответ 1

Используя getImageData и putImageData, вы можете легко реализовать пиксельно-пиксельный сдвиг. Например:

// shift everything to the left:
var imageData = context.getImageData(1, 0, context.canvas.width-1, context.canvas.height);
context.putImageData(imageData, 0, 0);
// now clear the right-most pixels:
context.clearRect(context.canvas.width-1, 0, 1, context.canvas.height);

Ответ 2

Отметьте этот пример jsFiddle, который использует ctx.translate и ctx.get/putImageData.

исходный код здесь

Как это было сделано:

Если перерисовать то, что вы хотите сдвинуть, не слишком медленно,

JS:

var canvas = document.getElementById( "canvas" ),
    ctx = canvas.getContext( "2d" );

var xOff = 0;
var redraw = function() {
        ctx.clearRect(0, 0, 600, 200);
        ctx.save();
        ctx.translate(xOff, 0);

        ctx.font = "100px Arial";
        ctx.fillText( "Google", 20, 130 );

        ctx.restore();
};

window.doIt = function() {
    xOff -= 25;
    redraw();
}

redraw();

var shiftContext = function(ctx, w, h, dx, dy) {
  var clamp = function(high, value) { return Math.max(0, Math.min(high, value)); };
  var imageData = ctx.getImageData(clamp(w, -dx), clamp(h, -dy), clamp(w, w-dx), clamp(h, h-dy));
  ctx.clearRect(0, 0, w, h);
  ctx.putImageData(imageData, 0, 0);
}

window.shiftImage = function() {
  shiftContext(ctx, 600, 200, -25, 0);   
}


var shiftContext = function(ctx, w, h, dx, dy) {
  var clamp = function(high, value) { return Math.max(0, Math.min(high, value)); };
  var imageData = ctx.getImageData(clamp(w, -dx), clamp(h, -dy), clamp(w, w-dx), clamp(h, h-dy));
  ctx.clearRect(0, 0, w, h);
  ctx.putImageData(imageData, 0, 0);
};

window.shiftImage = function() {
  shiftContext(ctx, 600, 200, -25, 0);   
};

Ответ 3

Отличные парни и спасибо. Здесь упрощенная версия кода ellisbben, работает для некоторых графиков прокрутки, которые я создаю:

function shift_canvas(ctx, w, h, dx, dy) {
  var imageData = ctx.getImageData(0, 0, w, h);
  ctx.clearRect(0, 0, w, h);
  ctx.putImageData(imageData, dx, dy);
}

Ответ 4

Мне было интересно, был ли удобный способ сделать это. Я закончил эту функцию перевода, которая не требует каких-либо (очень медленных) функций данных изображения:

function translate(x, y) {
    ctxBuffer.clearRect(0,0,canvasBuffer.width,canvasBuffer.height); //clear buffer
    ctxBuffer.drawImage(canvasDisplay,0,0); //store display data in buffer
    ctxDisplay.clearRect(0,0,canvasDisplay.width,canvasDisplay.height); //clear display
    ctxDisplay.drawImage(canvasBuffer,x,y); //copy buffer to display
}

Я сделал быструю демонстрацию этого здесь.

Ответ 5

Если вы хотите переместить все содержимое, вы можете использовать глобальную составную операцию копирования с помощью single drawImage(), создавая сам холст. Кажется, не работает в сафари, но он очень сумасшедший в хроме.

ctx.globalCompositeOperation = "copy";
ctx.drawImage(ctx.canvas,-widthOfMove, 0);
// reset back to normal for subsequent operations.
ctx.globalCompositeOperation = "source-over"