所以我知道HTML5画布像素方法与正常情况略有不同。我正在从Scala Swing应用程序移植光线跟踪器,其中旧的绘制方法如下所示:
for {
x <- pixels.s.indices
y <- pixels.s(x).indices
} {
g.setColor(pixels.s(x)(y))
g.fillRect(x, y, x, y)
}
其中pixels.s
是2D数组,如下所示:
[[Color, Color, Color],
[Color, Color, Color],
[Color, Color, Color]]
即。它精确映射到2D笛卡尔平面。
所以现在我稍微改变了一点,我有一个FLATTENED对象数组x
,y
和color
:
[{ x: 0, y: 0, color: { red: 33, green: 220, blue: 181 },
{ x: 0, y: 1, color: { red: 33, green: 220, blue: 231 },
{ x: 0, y: 2, color: { red: 33, green: 220, blue: 221 },
...
{ x: 319, y: 238, color: { red: 23, green: 10, blue: 31 },
{ x: 319, y: 239, color: { red: 13, green: 120, blue: 11 }]
我正在尝试使用以下代码将我扁平的颜色数组绘制到屏幕上:
var imageData = context.createImageData(width, height);
var numPixels = width*height;
for (var i = 0; i < numPixels; i++) {
imageData.data[(i*4)] = tracedScene[i].color.red;
imageData.data[(i*4) + 1] = tracedScene[i].color.green;
imageData.data[(i*4) + 2] = tracedScene[i].color.blue;
imageData.data[(i*4) + 3] = 255; // alpha color
};
context.putImageData(imageData, 0, 0);
但它出现了一点错误。我已经三次检查我的测试,实际的数组是正确的屏幕数据。我只是错误地渲染它。我现在正在接受这个:
我应该看到:
现在我在Swing版本(几年前)之前已经有了完全相同的图形怪异,这是因为我绘制图像的方式。我不记得我是怎么修的。
我希望能够做的是,有一些方法:
drawPixel(x, y, color, canvas) { ... }
能够使用颜色在x,y处绘制特定像素。或者......传统上这样做的方式。
答案 0 :(得分:1)
您的输入“扁平”数组的顺序错误:它应该是按行,但是您的列是按行。
[{ x: 0, y: 0, color: { red: 33, green: 220, blue: 181 },
{ x: 1, y: 0, color: { red: 33, green: 220, blue: 231 },
{ x: 2, y: 0, color: { red: 33, green: 220, blue: 221 },
...
(假设y从上到下,x - 从左到右)
答案 1 :(得分:1)
图片数据从(0, 0)
变为(1, 0)
,您的代码从(0, 0)
变为(0, 1)
。换句话说,行/列主要顺序存在冲突。
无论如何,根据你的表现需求,你可能会过度思考。
我希望能够做的是,有一些方法:
drawPixel(x, y, color, canvas) { ... }
能够在x,y上用颜色绘制特定像素。
为什么不填充单个像素?
ctx.fillStyle = 'rgba(red, green, blue, alpha)';
ctx.fillRect(x, y, 1, 1);
填充大约100像素效率不高,您需要切换到图像数据。
如果你想保持你的数据结构相同,你可以使用这样的东西,这应该有效:
var imageData = context.createImageData(width, height);
var numPixels = width*height;
var pixelCount = 0;
for (var i = 0; i < width; i++) {
for (var j = 0; j < height; j++) {
var wpixel = j * width * 4;
wpixel += i * 4;
console.log(wpixel);
imageData.data[(wpixel)] = tracedScene[pixelCount].red;
imageData.data[(wpixel) + 1] = tracedScene[pixelCount].green;
imageData.data[(wpixel) + 2] = tracedScene[pixelCount].blue;
imageData.data[(wpixel) + 3] = 255; // alpha color
pixelCount++; // independent of i and j the way I wrote it
}
}
context.putImageData(imageData, 0, 0);