我写了一个算法来通过billinear scalling方法来缩放图像,但它并没有像预期的那样工作。我真的找不到我的代码中的任何错误,但它产生了错误的输出:
Process(context: ImageData): ImageData {
var imageData = context;
var w = imageData.width;
var h = imageData.height;
var small = new Uint32Array((<any>imageData.data).buffer);
var big = new Uint32Array(small.length * (this.factor * this.factor));
var w2 = this.factor * imageData.width;
var h2 = this.factor * imageData.height;
var x_ratio = ((w) / w2);
var y_ratio = ((h) / h2);
for (var i = 0, f = h2; i < f; ++i) {
var py_a = (i * y_ratio);
var py = py_a | 0;
var py_t = py_a - py;
for (var j = 0, k = w2; j < k; ++j) {
var px_a = (j * x_ratio);
var px = px_a | 0;
var index = ((py * w) + px) | 0;
var px_t = px_a - px;
var fy1 = small[index] + (small[index + 1] - small[index]) * px_t;
var fy2 = small[index + w] + (small[index + w + 1] - small[index + w]) * px_t;
var tmp = fy1 + (fy2 - fy1) * py_t;
big[i * w2 + j] = tmp;
}
}
var ar = new Uint8ClampedArray(big.buffer);
var newImage = new ImageData(ar, w2, h2);
return newImage;
}
我通常想知道如果我可以一起对待每个频道,还是应该分开(至少是alpha)呢?
答案 0 :(得分:2)
必须拆分频道。他们都是。然后彼此独立插值。
否则它们将以奇怪的方式干涉,例如,如果您在纯白色和纯黑色之间进行插值而不进行分割,假设插值非常精细(大约2 24 像素宽),朝向黑色结束你变红(最低位的通道),渐渐变红,直到溢出成一个非常深的绿色,然后重新开始,但稍微多一点绿色混合,重复这个模式几次,直到最后重新开始再次,但蓝色混合在一起。更粗糙的插值基本上以规则的间隔对奇怪的彩虹进行采样。
分别对通道进行插值会使所有通道以相同的速率增加(并且不会定期回到零)朝向白色端,从而产生灰色渐变,这是预期的。
答案 1 :(得分:1)
如果数据是RGBA值(如harold所示),则下一个像素的相应分量不在下一个字节中,它距离四个字节,并且行的宽度不是{{ 1}}个字节,但w
个字节。
那会产生代码:
w * 4