PutImageData: примеры (JAVASCRIPT)

Руководство по применению метода putImageData для работы с пикселями
Раздел: Canvas, Пиксели
putImageData(imagedata: ImageData, dx: Number, dy: Number): undefined

Основная информация о функции putImageData

Метод putImageData() принадлежит к API Canvas 2D и применяется для отрисовки данных пикселей из объекта ImageData на элемент <canvas>. Эта функция используется при необходимости прямого манипулирования пикселями изображения, например, для применения фильтров, создания эффектов или низкоуровневой обработки графики.

Синтаксис:
context.putImageData(imageData, dx, dy [, dirtyX, dirtyY, dirtyWidth, dirtyHeight]);

Аргументы:

  • imageData (обязательный) – объект ImageData, содержащий массив данных о пикселях (значения red, green, blue, alpha).
  • dx (обязательный) – горизонтальная координата (в пикселях) левого верхнего угла области отрисовки на холсте.
  • dy (обязательный) – вертикальная координата (в пикселях) левого верхнего угла области отрисовки на холсте.
  • dirtyX (необязательный) – горизонтальная координата верхнего левого угла прямоугольной области внутри объекта ImageData, которая будет отрисована. По умолчанию равен 0.
  • dirtyY (необязательный) – вертикальная координата верхнего левого угла прямоугольной области внутри ImageData. По умолчанию 0.
  • dirtyWidth (необязательный) – ширина прямоугольной области внутри ImageData для отрисовки. По умолчанию равна ширине всего объекта ImageData.
  • dirtyHeight (необязательный) – высота прямоугольной области внутри ImageData для отрисовки. По умолчанию равна высоте всего объекта ImageData.

Возвращаемое значение: undefined.

Короткие примеры использования

Пример 1: Отрисовка всего объекта ImageData.

const canvas = document.getElementById('myCanvas');
const ctx = canvas.getContext('2d');
const imageData = ctx.createImageData(100, 100);
// Заполнение imageData данными...
ctx.putImageData(imageData, 0, 0);
На холст отрисовывается изображение 100x100 пикселей в координатах (0,0).

Пример 2: Отрисовка части объекта ImageData.

// dx, dy = 10,10. dirtyX, dirtyY = 20,20. dirtyWidth, dirtyHeight = 50,30.
ctx.putImageData(imageData, 10, 10, 20, 20, 50, 30);
На холст, начиная с точки (10,10), копируется фрагмент размером 50x30 пикселей из imageData, взятый с координат (20,20).

Пример 3: Использование только обязательных параметров.

ctx.putImageData(imageData, 50, 25);
Всё изображение из imageData отрисовывается на холсте, начиная с точки (50,25).

Похожие функции в JavaScript

drawImage() – метод для отрисовки готовых изображений (HTMLImageElement, другой canvas, видео) или его части на холст. Он работает с целыми изображениями, а не с массивами пикселей, и поддерживает масштабирование. Предпочтительнее для отрисовки готовой графики и текстур.

createImageData() / getImageData() – функции для создания нового пустого объекта ImageData и получения данных пикселей с холста соответственно. Они используются вместе с putImageData для полного цикла пиксельной обработки.

Альтернативы в других языках

Python (библиотека Pillow): Аналогом является метод putdata() объекта изображения.

from PIL import Image
img = Image.new('RGB', (100, 100))
data = [(255, 0, 0)] * (100 * 100) # Список кортежей RGB
img.putdata(data)
img.save('output.png')
Создается красное изображение 100x100 пикселей.

PHP (библиотека GD): Функция imagesetpixel() устанавливает цвет отдельного пикселя, а для блока данных используется цикл или imagecreatefromstring().

$im = imagecreatetruecolor(100, 100);
$red = imagecolorallocate($im, 255, 0, 0);
for ($x=0; $x<100; $x++) {
    for ($y=0; $y<100; $y++) {
        imagesetpixel($im, $x, $y, $red);
    }
}
imagepng($im, 'output.png');
Создается красное изображение 100x100 пикселей.

Основное отличие JavaScript-функции – это работа с предварительно сформированным объектом ImageData, содержащим плоский массив данных.

Типичные ошибки

1. Передача некорректного объекта ImageData.

const ctx = canvas.getContext('2d');
const wrongData = { data: [255,0,0,255], width:1, height:1 };
ctx.putImageData(wrongData, 0, 0); // Ошибка
Uncaught TypeError: Failed to execute 'putImageData' on 'CanvasRenderingContext2D': parameter 1 is not of type 'ImageData'.

2. Координаты или размеры dirty-прямоугольника выходят за границы ImageData.

const imageData = ctx.createImageData(10, 10);
ctx.putImageData(imageData, 0, 0, 5, 5, 10, 10); // dirtyWidth и dirtyHeight больше доступных
Отрисуется только часть прямоугольника, которая входит в границы ImageData (в данном случае 5x5 пикселей). Ошибка не генерируется.

3. Отрисовка за пределами холста. Данные, выходящие за границы canvas, просто обрезаются, без ошибки.

Изменения в последних версиях

Спецификация API Canvas 2D и функция putImageData() остаются стабильными в течение долгого времени. Существенных изменений в синтаксисе или поведении в последних версиях основных браузеров не было. Уточнения могут касаться обработки цветовых пространств или производительности, но базовый интерфейс неизменен.

Расширенные примеры

Пример 1: Инверсия цветов изображения на холсте.

Пример javascript
const canvas = document.getElementById('canvas');
const ctx = canvas.getContext('2d');
// Рисуем исходное изображение
ctx.fillStyle = 'rgb(100, 150, 200)';
ctx.fillRect(0, 0, 50, 50);
// Получаем данные
const imageData = ctx.getImageData(0, 0, 50, 50);
const data = imageData.data;
// Инвертируем цвета
for(let i = 0; i < data.length; i += 4) {
  data[i] = 255 - data[i];     // red
  data[i+1] = 255 - data[i+1]; // green
  data[i+2] = 255 - data[i+2]; // blue
}
// Возвращаем обработанные данные на холст
ctx.putImageData(imageData, 60, 0);
Рядом с исходным синим прямоугольником появляется его инвертированная оранжевая копия.

Пример 2: Создание эффекта шума с использованием частичной отрисовки.

Пример javascript
const imageData = ctx.createImageData(200, 200);
const data = imageData.data;
for(let i = 0; i < data.length; i+=4) {
    const value = Math.random() * 255;
    data[i] = data[i+1] = data[i+2] = value;
    data[i+3] = 255;
}
// Отрисовываем только центральную зашумленную область 100x100
ctx.putImageData(imageData, 50, 50, 50, 50, 100, 100);
На холсте в центре отрисовывается квадрат 100x100 пикселей с черно-белым шумом.

Пример 3: Построчное обновление холста (анимация).

Пример javascript
let row = 0;
const imageData = ctx.createImageData(canvas.width, 1); // Одна строка
function drawRow() {
    const data = imageData.data;
    for(let i=0; i
На холсте появляется анимированный эффект бегущей красной строки шума.

JS putImageData function comments

En
PutImageData Paints data from an ImageData object onto the canvas