@awayjs/stage
Version:
Stage for AwayJS
171 lines (170 loc) • 7.52 kB
JavaScript
import { Matrix, Point } from '@awayjs/core';
var BitmapImageUtils = /** @class */ (function () {
function BitmapImageUtils() {
}
BitmapImageUtils.drawBitmap = function (source, offsetX, offsetY, width, height, canvas, canvasOffsetX, canvasOffsetY, canvasImageWidth, canvasImageHeight, matrix) {
if (matrix === void 0) { matrix = null; }
if (matrix || (canvasImageWidth != width || canvasImageHeight != height)) {
if (!matrix) {
matrix = new Matrix();
matrix.scale(canvasImageWidth / width, canvasImageHeight / height);
}
var scaleX = Math.sqrt(matrix.a * matrix.a + matrix.b * matrix.b);
var scaleY = Math.sqrt(matrix.c * matrix.c + matrix.d * matrix.d);
var canvasWidth = width * scaleX;
var canvasHeight = height * scaleY;
matrix.tx += canvasOffsetX;
matrix.ty += canvasOffsetY;
canvasOffsetX = Math.floor(matrix.tx);
canvasOffsetY = Math.floor(matrix.ty);
matrix.invert();
if (scaleX >= 1 || scaleY >= 1) {
var p = new Point();
for (var i = canvasOffsetX; i < canvasOffsetX + canvasWidth; i++) {
for (var j = canvasOffsetY; j < canvasOffsetY + canvasHeight; j++) {
p.x = i;
p.y = j;
p = matrix.transformPoint(p);
var color = BitmapImageUtils.sampleBilinear(p.x, p.y, source, width, height);
BitmapImageUtils.applyPixel32(canvas, canvasImageWidth, canvasImageHeight, i, j, color);
}
}
}
else {
//decimate
var p1 = new Point();
var p2 = new Point();
for (var i = canvasOffsetX; i < canvasOffsetX + canvasWidth; i++) {
for (var j = canvasOffsetY; j < canvasOffsetY + canvasHeight; j++) {
p1.x = i;
p1.y = j;
p1 = matrix.transformPoint(p1);
p2.x = i + 1;
p2.y = j + 1;
p2 = matrix.transformPoint(p2);
var color = BitmapImageUtils.sampleBox(p1.x + offsetX, p1.y + offsetY, p2.x + offsetX, p2.y + offsetY, source, width, height);
BitmapImageUtils.applyPixel32(canvas, canvasImageWidth, canvasImageHeight, i, j, color);
}
}
}
matrix.invert();
}
else {
for (var i = canvasOffsetX; i < canvasOffsetX + width; i++) {
for (var j = canvasOffsetY; j < canvasOffsetY + height; j++) {
var color = BitmapImageUtils.sample(i - canvasOffsetX + offsetX, j - canvasOffsetY + offsetY, source, width, height);
BitmapImageUtils.applyPixel32(canvas, canvasImageWidth, canvasImageHeight, i, j, color);
}
}
}
};
BitmapImageUtils.applyPixel32 = function (data, width, height, x, y, color) {
//todo: blending support
x = Math.floor(x);
y = Math.floor(y);
if (x < 0 || x >= width || y >= height || y < 0)
return;
var index = (x + y * width) * 4;
//var alpha:number = color[3] / 255;
// target.data[index] += color[0];
// target.data[index + 1] += color[1];
// target.data[index + 2] += color[2];
// target.data[index + 3] += color[3];
data[index] = color[0];
data[index + 1] = color[1];
data[index + 2] = color[2];
data[index + 3] = color[3];
data[index] = data[index] & 0xFF;
data[index + 1] = data[index + 1] & 0xFF;
data[index + 2] = data[index + 2] & 0xFF;
data[index + 3] = data[index + 3] & 0xFF;
};
BitmapImageUtils.sampleBilinear = function (u, v, data, width, height, texelSizeX, texelSizeY) {
if (texelSizeX === void 0) { texelSizeX = 1; }
if (texelSizeY === void 0) { texelSizeY = 1; }
var color00 = BitmapImageUtils.sample(u, v, data, width, height);
var color10 = BitmapImageUtils.sample(u + texelSizeX, v, data, width, height);
var color01 = BitmapImageUtils.sample(u, v + texelSizeY, data, width, height);
var color11 = BitmapImageUtils.sample(u + texelSizeX, v + texelSizeY, data, width, height);
var a = u;
a = a - Math.floor(a);
var interColor0 = BitmapImageUtils.interpolateColor(color00, color10, a);
var interColor1 = BitmapImageUtils.interpolateColor(color01, color11, a);
var b = v;
b = b - Math.floor(b);
return BitmapImageUtils.interpolateColor(interColor0, interColor1, b);
};
BitmapImageUtils.sample = function (u, v, data, width, height) {
u = Math.floor(u);
v = Math.floor(v);
var result = [0, 0, 0, 0];
if (u < 0 || u >= width || v < 0 || v >= height) {
return result;
}
var index = (u + v * width) * 4;
result[0] = data[index];
result[1] = data[index + 1];
result[2] = data[index + 2];
result[3] = data[index + 3];
return result;
};
BitmapImageUtils.sampleBox = function (x0, y0, x1, y1, data, width, height) {
var area = 0; // -- total area accumulated in pixels
var result = [0, 0, 0, 0];
var x;
var y;
var xsize;
var ysize;
var fromY = Math.floor(y0);
var toY = Math.ceil(y1);
fromY = Math.max(Math.min(fromY, height - 1), 0);
toY = Math.max(Math.min(toY, height - 1), 0);
for (y = fromY; y < toY; y++) {
ysize = 1;
if (y < y0) {
ysize = ysize * (1.0 - (y0 - y));
}
if (y > y1) {
ysize = ysize * (1.0 - (y - y1));
}
var fromX = Math.floor(x0);
var toX = Math.ceil(x1);
fromX = Math.max(Math.min(fromX, width - 1), 0);
toX = Math.max(Math.min(toX, width - 1), 0);
for (x = fromX; x < toX; x++) {
xsize = ysize;
var color = BitmapImageUtils.sample(x, y, data, width, height);
if (x < x0) {
xsize = xsize * (1.0 - (x0 - x));
}
if (x > x1) {
xsize = xsize * (1.0 - (x - x1));
}
result[0] += color[0] * xsize;
result[1] += color[1] * xsize;
result[2] += color[2] * xsize;
result[3] += color[3] * xsize;
area = area + xsize;
}
}
result[0] /= area;
result[1] /= area;
result[2] /= area;
result[3] /= area;
result[0] = result[0] & 0xFF;
result[1] = result[1] & 0xFF;
result[2] = result[2] & 0xFF;
result[3] = result[3] & 0xFF;
return result;
};
BitmapImageUtils.interpolateColor = function (source, target, a) {
var result = [];
result[0] = source[0] + (target[0] - source[0]) * a;
result[1] = source[1] + (target[1] - source[1]) * a;
result[2] = source[2] + (target[2] - source[2]) * a;
result[3] = source[3] + (target[3] - source[3]) * a;
return result;
};
return BitmapImageUtils;
}());
export { BitmapImageUtils };