javascript - 试图从画布上的像素数组绘制图像
问题描述
我有一个 256 个值的像素数组,看起来像这样:
[-7.440151952041672e-45, -3.549412689007182e-44, -1.6725845544560632e-43, -7.785321621854041e-43, -3.579496378208359e-42, -1.6256392941914181e-41, ...]
我想要实现的是,将此像素阵列图像绘制到画布上。我需要这个的原因是因为我需要根据卷积值重新计算像素数组,以使用特定的过滤器重绘图像。
我目前正在尝试使用以下方法绘制它:
function generate_image() {
// create an offscreen canvas
var canvas = document.createElement('canvas');
canvas.setAttribute("id", "canvas_id");
canvas.style.cssText = 'width: 400px; height: 400px; z-index: 1;';
document.body.appendChild(canvas);
var ctx=canvas.getContext("2d");
var images = generate_image_array_data();
// This is the pixel array of the image
var image = images[2];
var palette = ctx.getImageData(0, 0, 160, 120);
palette.data.set(new Uint8ClampedArray(image));
ctx.putImageData(palette, 0, 0);
}
使用上面的代码,画布上什么也没有发生。我相当肯定我做错了什么,但我不确定是什么。如果有人能够指出我正确的方向,那将不胜感激。
解决方案
您显示的日志不能是 Uint8ClampedArray 之一。
Clamped Uint8 值不能为负数,也不能为浮点数。
因此,这些要么是 32 位浮点值,要么是 64 位浮点值。
一旦确定它是哪个,就可以通过执行将其转换为钳制的 Uint8 值
const data = new Uint8ClampedArray( original_data.buffer );
iforiginal_data
已经是一个 TypedArray。
如果不是,而是一个普通的数组,您必须首先从该数组中的值重建一个 TypedArray,然后进行相同的转换。
假设 64 位浮点值:
const data = new Uint8ClampedArray( new Float64Array( images[ 2 ] ).buffer );
const palette = new ImageData( data, 160, 120 );
generate_image();
function generate_image() {
// create an offscreen canvas
var canvas = document.createElement('canvas');
canvas.setAttribute("id", "canvas_id");
canvas.style.cssText = 'width: 400px; height: 400px; z-index: 1;';
document.body.appendChild(canvas);
var ctx=canvas.getContext("2d");
var images = generate_image_array_data();
// This is the pixel array of the image
var image = images[2];
var data = new Uint8ClampedArray( new Float64Array( image ).buffer );
var palette = new ImageData(data, 3,4);
ctx.putImageData(palette, 0, 0);
ctx.imageSmootingEnabled = false;
ctx.globalCompositeOperation = "copy";
ctx.drawImage(canvas, 0, 0, 3, 4, 0, 0, canvas.width, canvas.height);
}
function generate_image_array_data() {
return [, , [-7.440151952041672e-45, -3.549412689007182e-44, -1.6725845544560632e-43, -7.785321621854041e-43, -3.579496378208359e-42, -1.6256392941914181e-41 ] ];
}
PS:如果您不需要画布上的像素,请不要调用 getImageData,更喜欢 ctx.createImageData(width, height) 甚至 new ImageData(width, height),这将避免您的画布位图缓冲区(缓慢)从 GPU 转移到 CPU
推荐阅读
- distributed-computing - 如何理解 CAP 定理中的“可用数据对象”?
- node.js - docker在我运行docker image时生成节点程序映像执行此错误
- android - 如何在 Android kotlin 中使用 Google Analytics
- java - 为什么要在 Scala 中扩展 Serializable?
- angular - docker 究竟如何使用 docker run 命令从我的本地加载代码?
- sql - 如何在 LinQ Lambda 中按父级分组并对其子级应用聚合函数
- ios - Apple Appstore - 从应用程序直接向苹果应用程序商店发布评级
- windows - exec basename 不能从 Windows makefile 工作
- php - 从php获取nodejs中的跨源资源
- laravel - 客户端错误:`POST https://graph.facebook.com/v3.0/oauth/access_token` 导致`400 Bad Request`