yem*_*mon 3 html javascript canvas
一个 5 x 5 像素的图像数据在线性化图像数据数组中是这样的 -
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 , 0, 0, 0, 0, 0, 0, 240, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 240, 0, 0 , 0, 255 , 0, 0, 0, 240, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 240, 0, 0, 0 , 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
所以,3x3 像素数据是- 0 0 0 255。我怎样才能得到相邻的像素位置?左右相邻的很容易,分别是负4和正4。
来自的像素数据.getImageData().data是 aTypedArray类型Uint8ClampedArray。读取值时,它们将在 0-255 的范围内,并按红色、绿色、蓝色、Alpha 的顺序排列。如果 alpha 的值为零,则红色、绿色和蓝色也将为零。
获取像素的索引
const imageData = ctx.getImageData(0,0,ctx.canvas.width, ctx.canvas.height);
var index = (x + y * imageData.width) * 4;
const red = imageData.data[index];
const green = imageData.data[index + 1];
const blue = imageData.data[index + 2];
const alpha = imageData.data[index + 3];
Run Code Online (Sandbox Code Playgroud)
向下移动一个像素
index += imageData.width * 4;
Run Code Online (Sandbox Code Playgroud)
向上移动一个
index -= imageData.width * 4;
Run Code Online (Sandbox Code Playgroud)
向左移动。
index -= 4;
Run Code Online (Sandbox Code Playgroud)
向右移动
index += 4;
Run Code Online (Sandbox Code Playgroud)
如果您在左侧或右侧边缘,并且沿边缘方向移动,则将环绕,如果向左移动则在上方和右侧的线上,如果向下移动则在下方和左侧的线上。
设置图像数据时,这些值将被限制并限制为 0-255
imageData.data[index] = 29.5
console.log(imageData.data[index]); // 29
imageData.data[index] = -283
console.log(imageData.data[index]); // 0
imageData.data[index] = 283
console.log(imageData.data[index]); // 255
Run Code Online (Sandbox Code Playgroud)
如果您设置的索引超出数组大小,它将被忽略
imageData.data[-100] = 255;
console.log(imageData.data[-100]); // Undefined
imageData.data[imageData.data.length + 4] = 255;
console.log(imageData.data[imageData.data.length + 4]); // Undefined
Run Code Online (Sandbox Code Playgroud)
您可以通过使用不同的数组类型来加快访问和处理速度。例如,一个像素的所有通道作为一个值使用Uint32Array
const imageData = ctx.getImageData(0,0,ctx.canvas.width, ctx.canvas.height);
const pixels = new Uint32Array(imageData.data.buffer);
var index32 = x + y * imageData.width; // note there is no 4*;
const pixel = pixels[index32];
Run Code Online (Sandbox Code Playgroud)
通道存储在位 31-24 Alpha、23-16 蓝色、15-8 绿色、7-0 红色中。
您可以使用十六进制值设置像素
pixels[x + y * imageData.width] = 0xFF0000FF; // red
pixels[x + y * imageData.width] = 0xFF00FF00; // Green
pixels[x + y * imageData.width] = 0xFFFF0000; // Blue
pixels[x + y * imageData.width] = 0xFF000000; // Black
pixels[x + y * imageData.width] = 0xFFFFFFFF; // White
pixels[x + y * imageData.width] = 0; // Transparent
Run Code Online (Sandbox Code Playgroud)
您可以在一次调用中设置所有像素
pixels.fill(0xFF000000); // all pixels black
Run Code Online (Sandbox Code Playgroud)
您可以使用以下命令将数组数据复制到数组上
// set 3 pixels in a row at x,y Red, Yellow, White
pixels.set([0xFF0000FF,0xFF00FFFF,0xFFFFFFFF], x+y * imageData.width);
Run Code Online (Sandbox Code Playgroud)
如果画布有任何来自不受信任来源的像素,它将被污染,您将无法读取像素数据。可信源是相同的域或图像,并带有适当的 CORS 标头信息。文件系统上的图像无法访问其像素。一旦画布被污染,就无法清洁。
当您调用ctx.getImageData(0,0,1,1,)MDN 出于某种原因未列出此异常时,受污染的画布将引发错误。你会看到“SecurityError”DOMException;在 DevTools 控制台中,StackOverflow 中有很多关于该主题的已回答问题。
| 归档时间: |
|
| 查看次数: |
830 次 |
| 最近记录: |