imagescript 1.2.15 → 1.2.17
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/ImageScript.d.ts +233 -223
- package/ImageScript.js +1658 -1646
- package/LICENSE +12 -619
- package/LICENSE.AGPL-3.0 +619 -0
- package/LICENSE.MIT +19 -0
- package/README.md +51 -46
- package/bench/_.mjs +165 -165
- package/bench/all.mjs +3 -3
- package/bench/blur.mjs +58 -58
- package/bench/flip.mjs +62 -62
- package/bench/overlay.mjs +34 -34
- package/bench/package.json +6 -6
- package/bench/readme.md +63 -63
- package/bench/resize.mjs +51 -51
- package/codecs/LICENSE +20 -20
- package/codecs/lib.d.ts +49 -49
- package/codecs/lib.js +5 -5
- package/codecs/node/index.js +2 -2
- package/codecs/node/index.mjs +5 -5
- package/codecs/package.json +13 -13
- package/codecs/readme.md +37 -37
- package/package.json +41 -41
- package/png/node.js +1137 -1137
- package/png/src/crc.mjs +48 -48
- package/png/src/mem.mjs +23 -23
- package/png/src/png.mjs +254 -254
- package/png/src/zlib.mjs +617 -617
- package/tsconfig.json +21 -21
- package/utils/mem.js +25 -25
- package/v2/codecs/magic.js +24 -24
- package/v2/framebuffer.d.ts +66 -66
- package/v2/framebuffer.js +2352 -2352
- package/v2/framebuffer.mjs +125 -125
- package/v2/framebuffer.rs +1263 -1263
- package/v2/index.d.ts +83 -83
- package/v2/index.js +260 -260
- package/v2/ops/blur.mjs +302 -302
- package/v2/ops/color.mjs +276 -276
- package/v2/ops/crop.mjs +63 -63
- package/v2/ops/fill.mjs +32 -32
- package/v2/ops/flip.mjs +32 -32
- package/v2/ops/index.mjs +8 -8
- package/v2/ops/iterator.mjs +33 -33
- package/v2/ops/overlay.mjs +62 -62
- package/v2/ops/resize.mjs +165 -165
- package/v2/ops/rotate.mjs +116 -116
- package/v2/util/mem.mjs +23 -23
- package/wasm/node/font.js +141 -141
- package/wasm/node/gif.js +76 -76
- package/wasm/node/jpeg.js +91 -91
- package/wasm/node/png.js +49 -49
- package/wasm/node/svg.js +55 -55
- package/wasm/node/tiff.js +46 -46
package/v2/ops/crop.mjs
CHANGED
|
@@ -1,64 +1,64 @@
|
|
|
1
|
-
function clamp(min, int, max) {
|
|
2
|
-
const t = int < min ? min : int; return t > max ? max : t;
|
|
3
|
-
}
|
|
4
|
-
|
|
5
|
-
export function cut(x, y, width, height, framebuffer) {
|
|
6
|
-
width |= 0;
|
|
7
|
-
height |= 0;
|
|
8
|
-
const frame = new framebuffer.constructor(width, height);
|
|
9
|
-
|
|
10
|
-
const n32 = frame.u32;
|
|
11
|
-
const o32 = framebuffer.u32;
|
|
12
|
-
const fwidth = framebuffer.width | 0;
|
|
13
|
-
|
|
14
|
-
for (let yy = 0 | 0; yy < height; yy++) {
|
|
15
|
-
const offset = x + fwidth * (y + yy);
|
|
16
|
-
n32.set(o32.subarray(offset, width + offset), yy * width);
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
return frame;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
export function crop(x, y, width, height, framebuffer) {
|
|
23
|
-
width |= 0;
|
|
24
|
-
height |= 0;
|
|
25
|
-
const old = framebuffer.u32;
|
|
26
|
-
const fwidth = framebuffer.width | 0;
|
|
27
|
-
const u32 = framebuffer.u32 = new Uint32Array(width * height);
|
|
28
|
-
|
|
29
|
-
for (let yy = 0; yy < height; yy++) {
|
|
30
|
-
const offset = x + fwidth * (y + yy);
|
|
31
|
-
u32.set(old.subarray(offset, width + offset), yy * width);
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
framebuffer.width = width;
|
|
35
|
-
framebuffer.height = height;
|
|
36
|
-
framebuffer.u8 = new Uint8Array(framebuffer.u32.buffer);
|
|
37
|
-
framebuffer.view = new DataView(framebuffer.u32.buffer);
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
export function circle(feathering, framebuffer) {
|
|
41
|
-
const u8 = framebuffer.u8;
|
|
42
|
-
const u32 = framebuffer.u32;
|
|
43
|
-
const width = framebuffer.width | 0;
|
|
44
|
-
const height = framebuffer.height | 0;
|
|
45
|
-
const rad = Math.min(width, height) / 2;
|
|
46
|
-
|
|
47
|
-
const cx = width / 2;
|
|
48
|
-
const cy = height / 2;
|
|
49
|
-
const rad_2 = rad ** 2;
|
|
50
|
-
const feathering_12 = feathering ** (1 / 2);
|
|
51
|
-
|
|
52
|
-
for (let y = 0 | 0; y < height; y++) {
|
|
53
|
-
const cdy = (y - cy) ** 2;
|
|
54
|
-
const y_offset = y * width;
|
|
55
|
-
|
|
56
|
-
for (let x = 0 | 0; x < width; x++) {
|
|
57
|
-
const cd = cdy + (x - cx) ** 2;
|
|
58
|
-
if (cd > rad_2) u32[x + y_offset] = 0;
|
|
59
|
-
else if (feathering) u8[3 + 4 * (x + y_offset)] *= clamp(0, 1 - (cd / rad_2) * feathering_12, 1);
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
return framebuffer;
|
|
1
|
+
function clamp(min, int, max) {
|
|
2
|
+
const t = int < min ? min : int; return t > max ? max : t;
|
|
3
|
+
}
|
|
4
|
+
|
|
5
|
+
export function cut(x, y, width, height, framebuffer) {
|
|
6
|
+
width |= 0;
|
|
7
|
+
height |= 0;
|
|
8
|
+
const frame = new framebuffer.constructor(width, height);
|
|
9
|
+
|
|
10
|
+
const n32 = frame.u32;
|
|
11
|
+
const o32 = framebuffer.u32;
|
|
12
|
+
const fwidth = framebuffer.width | 0;
|
|
13
|
+
|
|
14
|
+
for (let yy = 0 | 0; yy < height; yy++) {
|
|
15
|
+
const offset = x + fwidth * (y + yy);
|
|
16
|
+
n32.set(o32.subarray(offset, width + offset), yy * width);
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
return frame;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
export function crop(x, y, width, height, framebuffer) {
|
|
23
|
+
width |= 0;
|
|
24
|
+
height |= 0;
|
|
25
|
+
const old = framebuffer.u32;
|
|
26
|
+
const fwidth = framebuffer.width | 0;
|
|
27
|
+
const u32 = framebuffer.u32 = new Uint32Array(width * height);
|
|
28
|
+
|
|
29
|
+
for (let yy = 0; yy < height; yy++) {
|
|
30
|
+
const offset = x + fwidth * (y + yy);
|
|
31
|
+
u32.set(old.subarray(offset, width + offset), yy * width);
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
framebuffer.width = width;
|
|
35
|
+
framebuffer.height = height;
|
|
36
|
+
framebuffer.u8 = new Uint8Array(framebuffer.u32.buffer);
|
|
37
|
+
framebuffer.view = new DataView(framebuffer.u32.buffer);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
export function circle(feathering, framebuffer) {
|
|
41
|
+
const u8 = framebuffer.u8;
|
|
42
|
+
const u32 = framebuffer.u32;
|
|
43
|
+
const width = framebuffer.width | 0;
|
|
44
|
+
const height = framebuffer.height | 0;
|
|
45
|
+
const rad = Math.min(width, height) / 2;
|
|
46
|
+
|
|
47
|
+
const cx = width / 2;
|
|
48
|
+
const cy = height / 2;
|
|
49
|
+
const rad_2 = rad ** 2;
|
|
50
|
+
const feathering_12 = feathering ** (1 / 2);
|
|
51
|
+
|
|
52
|
+
for (let y = 0 | 0; y < height; y++) {
|
|
53
|
+
const cdy = (y - cy) ** 2;
|
|
54
|
+
const y_offset = y * width;
|
|
55
|
+
|
|
56
|
+
for (let x = 0 | 0; x < width; x++) {
|
|
57
|
+
const cd = cdy + (x - cx) ** 2;
|
|
58
|
+
if (cd > rad_2) u32[x + y_offset] = 0;
|
|
59
|
+
else if (feathering) u8[3 + 4 * (x + y_offset)] *= clamp(0, 1 - (cd / rad_2) * feathering_12, 1);
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
return framebuffer;
|
|
64
64
|
}
|
package/v2/ops/fill.mjs
CHANGED
|
@@ -1,33 +1,33 @@
|
|
|
1
|
-
export function color(int, framebuffer) {
|
|
2
|
-
framebuffer.view.setUint32(0, int);
|
|
3
|
-
framebuffer.u32.fill(framebuffer.u32[0]);
|
|
4
|
-
}
|
|
5
|
-
|
|
6
|
-
export function fn(cb, framebuffer) {
|
|
7
|
-
let offset = 0 | 0;
|
|
8
|
-
const view = framebuffer.view;
|
|
9
|
-
const width = framebuffer.width | 0;
|
|
10
|
-
const height = framebuffer.height | 0;
|
|
11
|
-
|
|
12
|
-
for (let y = 1 | 0; y <= height; y++) {
|
|
13
|
-
for (let x = 1 | 0; x <= width; x++) {
|
|
14
|
-
view.setUint32(offset, cb(x, y), false); offset += 4;
|
|
15
|
-
}
|
|
16
|
-
}
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
export function swap(old, int, framebuffer) {
|
|
20
|
-
{
|
|
21
|
-
const t = new Uint32Array(2);
|
|
22
|
-
const v = new DataView(t.buffer);
|
|
23
|
-
old = (v.setUint32(0, old), t[0]);
|
|
24
|
-
int = (v.setUint32(4, int), t[1]);
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
const u32 = framebuffer.u32;
|
|
28
|
-
const l = framebuffer.u32.length | 0;
|
|
29
|
-
|
|
30
|
-
for (let o = 0 | 0; o < l; o++) {
|
|
31
|
-
if (old === u32[o]) u32[o] = int;
|
|
32
|
-
}
|
|
1
|
+
export function color(int, framebuffer) {
|
|
2
|
+
framebuffer.view.setUint32(0, int);
|
|
3
|
+
framebuffer.u32.fill(framebuffer.u32[0]);
|
|
4
|
+
}
|
|
5
|
+
|
|
6
|
+
export function fn(cb, framebuffer) {
|
|
7
|
+
let offset = 0 | 0;
|
|
8
|
+
const view = framebuffer.view;
|
|
9
|
+
const width = framebuffer.width | 0;
|
|
10
|
+
const height = framebuffer.height | 0;
|
|
11
|
+
|
|
12
|
+
for (let y = 1 | 0; y <= height; y++) {
|
|
13
|
+
for (let x = 1 | 0; x <= width; x++) {
|
|
14
|
+
view.setUint32(offset, cb(x, y), false); offset += 4;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
export function swap(old, int, framebuffer) {
|
|
20
|
+
{
|
|
21
|
+
const t = new Uint32Array(2);
|
|
22
|
+
const v = new DataView(t.buffer);
|
|
23
|
+
old = (v.setUint32(0, old), t[0]);
|
|
24
|
+
int = (v.setUint32(4, int), t[1]);
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
const u32 = framebuffer.u32;
|
|
28
|
+
const l = framebuffer.u32.length | 0;
|
|
29
|
+
|
|
30
|
+
for (let o = 0 | 0; o < l; o++) {
|
|
31
|
+
if (old === u32[o]) u32[o] = int;
|
|
32
|
+
}
|
|
33
33
|
}
|
package/v2/ops/flip.mjs
CHANGED
|
@@ -1,33 +1,33 @@
|
|
|
1
|
-
export function horizontal(framebuffer) {
|
|
2
|
-
let offset = 0 | 0;
|
|
3
|
-
const u32 = framebuffer.u32;
|
|
4
|
-
const width = framebuffer.width | 0;
|
|
5
|
-
const height = framebuffer.height | 0;
|
|
6
|
-
|
|
7
|
-
for (let y = 0 | 0; y < height; y++) {
|
|
8
|
-
u32.subarray(offset, offset += width).reverse();
|
|
9
|
-
}
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
export function vertical(framebuffer) {
|
|
13
|
-
const u32 = framebuffer.u32;
|
|
14
|
-
const width = framebuffer.width | 0;
|
|
15
|
-
const oheight = framebuffer.height | 0;
|
|
16
|
-
const height = (framebuffer.height / 2) | 0;
|
|
17
|
-
|
|
18
|
-
for (let y = 0 | 0; y < height; y++) {
|
|
19
|
-
const yo = y * width | 0;
|
|
20
|
-
const wo1y = width * (oheight - 1 - y) | 0;
|
|
21
|
-
|
|
22
|
-
for (let x = 0 | 0; x < width; x++) {
|
|
23
|
-
const offset = x + yo;
|
|
24
|
-
const offset2 = x + wo1y;
|
|
25
|
-
|
|
26
|
-
const top = u32[offset];
|
|
27
|
-
const bottom = u32[offset2];
|
|
28
|
-
|
|
29
|
-
u32[offset2] = top;
|
|
30
|
-
u32[offset] = bottom;
|
|
31
|
-
}
|
|
32
|
-
}
|
|
1
|
+
export function horizontal(framebuffer) {
|
|
2
|
+
let offset = 0 | 0;
|
|
3
|
+
const u32 = framebuffer.u32;
|
|
4
|
+
const width = framebuffer.width | 0;
|
|
5
|
+
const height = framebuffer.height | 0;
|
|
6
|
+
|
|
7
|
+
for (let y = 0 | 0; y < height; y++) {
|
|
8
|
+
u32.subarray(offset, offset += width).reverse();
|
|
9
|
+
}
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
export function vertical(framebuffer) {
|
|
13
|
+
const u32 = framebuffer.u32;
|
|
14
|
+
const width = framebuffer.width | 0;
|
|
15
|
+
const oheight = framebuffer.height | 0;
|
|
16
|
+
const height = (framebuffer.height / 2) | 0;
|
|
17
|
+
|
|
18
|
+
for (let y = 0 | 0; y < height; y++) {
|
|
19
|
+
const yo = y * width | 0;
|
|
20
|
+
const wo1y = width * (oheight - 1 - y) | 0;
|
|
21
|
+
|
|
22
|
+
for (let x = 0 | 0; x < width; x++) {
|
|
23
|
+
const offset = x + yo;
|
|
24
|
+
const offset2 = x + wo1y;
|
|
25
|
+
|
|
26
|
+
const top = u32[offset];
|
|
27
|
+
const bottom = u32[offset2];
|
|
28
|
+
|
|
29
|
+
u32[offset2] = top;
|
|
30
|
+
u32[offset] = bottom;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
33
|
}
|
package/v2/ops/index.mjs
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
export * as flip from './flip.mjs';
|
|
2
|
-
export * as fill from './fill.mjs';
|
|
3
|
-
export * as blur from './blur.mjs';
|
|
4
|
-
export * as crop from './crop.mjs';
|
|
5
|
-
export * as color from './color.mjs';
|
|
6
|
-
export * as resize from './resize.mjs';
|
|
7
|
-
export * as rotate from './rotate.mjs';
|
|
8
|
-
export * as overlay from './overlay.mjs';
|
|
1
|
+
export * as flip from './flip.mjs';
|
|
2
|
+
export * as fill from './fill.mjs';
|
|
3
|
+
export * as blur from './blur.mjs';
|
|
4
|
+
export * as crop from './crop.mjs';
|
|
5
|
+
export * as color from './color.mjs';
|
|
6
|
+
export * as resize from './resize.mjs';
|
|
7
|
+
export * as rotate from './rotate.mjs';
|
|
8
|
+
export * as overlay from './overlay.mjs';
|
|
9
9
|
export * as iterator from './iterator.mjs';
|
package/v2/ops/iterator.mjs
CHANGED
|
@@ -1,34 +1,34 @@
|
|
|
1
|
-
export function* cords(framebuffer) {
|
|
2
|
-
const width = framebuffer.width | 0;
|
|
3
|
-
const height = framebuffer.height | 0;
|
|
4
|
-
|
|
5
|
-
for (let y = 0 | 0; y < height; y++) {
|
|
6
|
-
for (let x = 0 | 0; x < width; x++) yield [x, y];
|
|
7
|
-
}
|
|
8
|
-
}
|
|
9
|
-
|
|
10
|
-
export function* rgba(framebuffer) {
|
|
11
|
-
let offset = 0 | 0;
|
|
12
|
-
const u8 = framebuffer.u8;
|
|
13
|
-
const width = framebuffer.width | 0;
|
|
14
|
-
const height = framebuffer.height | 0;
|
|
15
|
-
|
|
16
|
-
for (let y = 0 | 0; y < height; y++) {
|
|
17
|
-
for (let x = 0 | 0; x < width; x++) {
|
|
18
|
-
yield [x, y, u8.subarray(offset, offset += 4)];
|
|
19
|
-
}
|
|
20
|
-
}
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
export function* u32(framebuffer) {
|
|
24
|
-
let offset = 0 | 0;
|
|
25
|
-
const view = framebuffer.view;
|
|
26
|
-
const width = framebuffer.width | 0;
|
|
27
|
-
const height = framebuffer.height | 0;
|
|
28
|
-
|
|
29
|
-
for (let y = 0 | 0; y < height; y++) {
|
|
30
|
-
for (let x = 0 | 0; x < width; x++) {
|
|
31
|
-
yield [x, y, view.getUint32(offset, false)]; offset += 4;
|
|
32
|
-
}
|
|
33
|
-
}
|
|
1
|
+
export function* cords(framebuffer) {
|
|
2
|
+
const width = framebuffer.width | 0;
|
|
3
|
+
const height = framebuffer.height | 0;
|
|
4
|
+
|
|
5
|
+
for (let y = 0 | 0; y < height; y++) {
|
|
6
|
+
for (let x = 0 | 0; x < width; x++) yield [x, y];
|
|
7
|
+
}
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
export function* rgba(framebuffer) {
|
|
11
|
+
let offset = 0 | 0;
|
|
12
|
+
const u8 = framebuffer.u8;
|
|
13
|
+
const width = framebuffer.width | 0;
|
|
14
|
+
const height = framebuffer.height | 0;
|
|
15
|
+
|
|
16
|
+
for (let y = 0 | 0; y < height; y++) {
|
|
17
|
+
for (let x = 0 | 0; x < width; x++) {
|
|
18
|
+
yield [x, y, u8.subarray(offset, offset += 4)];
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export function* u32(framebuffer) {
|
|
24
|
+
let offset = 0 | 0;
|
|
25
|
+
const view = framebuffer.view;
|
|
26
|
+
const width = framebuffer.width | 0;
|
|
27
|
+
const height = framebuffer.height | 0;
|
|
28
|
+
|
|
29
|
+
for (let y = 0 | 0; y < height; y++) {
|
|
30
|
+
for (let x = 0 | 0; x < width; x++) {
|
|
31
|
+
yield [x, y, view.getUint32(offset, false)]; offset += 4;
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
34
|
}
|
package/v2/ops/overlay.mjs
CHANGED
|
@@ -1,63 +1,63 @@
|
|
|
1
|
-
export function replace(bg, fg, x, y) {
|
|
2
|
-
const b32 = bg.u32;
|
|
3
|
-
const f32 = fg.u32;
|
|
4
|
-
const fw = fg.width | 0;
|
|
5
|
-
const bw = bg.width | 0;
|
|
6
|
-
const fh = fg.height | 0;
|
|
7
|
-
const bh = bg.height | 0;
|
|
8
|
-
const ox = (x > 0 ? 0 : -x) | 0;
|
|
9
|
-
const oy = (y > 0 ? 0 : -y) | 0;
|
|
10
|
-
const top = (y > 0 ? y : 0) | 0;
|
|
11
|
-
const left = (x > 0 ? x : 0) | 0;
|
|
12
|
-
const width = (Math.min(bw, x + fw) - left) | 0;
|
|
13
|
-
const height = (Math.min(bh, y + fh) - top) | 0;
|
|
14
|
-
|
|
15
|
-
if (0 >= width || 0 >= height) return;
|
|
16
|
-
|
|
17
|
-
for (let yy = 0 | 0; yy < height; yy++) {
|
|
18
|
-
const yyoffset = ox + fw * (yy + oy);
|
|
19
|
-
const yoffset = left + bw * (yy + top);
|
|
20
|
-
b32.subarray(yoffset, width + yoffset).set(f32.subarray(yyoffset, width + yyoffset));
|
|
21
|
-
}
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
export function blend(bg, fg, x, y) {
|
|
25
|
-
const b32 = bg.u32;
|
|
26
|
-
const f32 = fg.u32;
|
|
27
|
-
const fw = fg.width | 0;
|
|
28
|
-
const bw = bg.width | 0;
|
|
29
|
-
const fh = fg.height | 0;
|
|
30
|
-
const bh = bg.height | 0;
|
|
31
|
-
const ox = (x > 0 ? 0 : -x) | 0;
|
|
32
|
-
const oy = (y > 0 ? 0 : -y) | 0;
|
|
33
|
-
const top = (y > 0 ? y : 0) | 0;
|
|
34
|
-
const left = (x > 0 ? x : 0) | 0;
|
|
35
|
-
const width = (Math.min(bw, x + fw) - left) | 0;
|
|
36
|
-
const height = (Math.min(bh, y + fh) - top) | 0;
|
|
37
|
-
|
|
38
|
-
if (0 >= width || 0 >= height) return;
|
|
39
|
-
|
|
40
|
-
for (let yy = 0 | 0; yy < height; yy++) {
|
|
41
|
-
const yyoffset = ox + fw * (yy + oy);
|
|
42
|
-
const yoffset = left + bw * (yy + top);
|
|
43
|
-
|
|
44
|
-
for (let xx = 0 | 0; xx < width; xx++) {
|
|
45
|
-
const F = f32[xx + yyoffset];
|
|
46
|
-
|
|
47
|
-
// todo: be?
|
|
48
|
-
const fa = F >> 24 & 0xff;
|
|
49
|
-
if (fa === 0x00) continue;
|
|
50
|
-
else if (fa === 0xff) b32[xx + yoffset] = F;
|
|
51
|
-
|
|
52
|
-
else {
|
|
53
|
-
const alpha = 1 + fa;
|
|
54
|
-
const inv_alpha = 256 - fa;
|
|
55
|
-
const B = b32[xx + yoffset];
|
|
56
|
-
const r = (alpha * (F & 0xff) + inv_alpha * (B & 0xff)) >> 8;
|
|
57
|
-
const g = (alpha * ((F >> 8) & 0xff) + inv_alpha * ((B >> 8) & 0xff)) >> 8;
|
|
58
|
-
const b = (alpha * ((F >> 16) & 0xff) + inv_alpha * ((B >> 16) & 0xff)) >> 8;
|
|
59
|
-
b32[xx + yoffset] = (Math.max(fa, (B >> 24) & 0xff) << 24) | ((b & 0xff) << 16) | ((g & 0xff) << 8) | r;
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
}
|
|
1
|
+
export function replace(bg, fg, x, y) {
|
|
2
|
+
const b32 = bg.u32;
|
|
3
|
+
const f32 = fg.u32;
|
|
4
|
+
const fw = fg.width | 0;
|
|
5
|
+
const bw = bg.width | 0;
|
|
6
|
+
const fh = fg.height | 0;
|
|
7
|
+
const bh = bg.height | 0;
|
|
8
|
+
const ox = (x > 0 ? 0 : -x) | 0;
|
|
9
|
+
const oy = (y > 0 ? 0 : -y) | 0;
|
|
10
|
+
const top = (y > 0 ? y : 0) | 0;
|
|
11
|
+
const left = (x > 0 ? x : 0) | 0;
|
|
12
|
+
const width = (Math.min(bw, x + fw) - left) | 0;
|
|
13
|
+
const height = (Math.min(bh, y + fh) - top) | 0;
|
|
14
|
+
|
|
15
|
+
if (0 >= width || 0 >= height) return;
|
|
16
|
+
|
|
17
|
+
for (let yy = 0 | 0; yy < height; yy++) {
|
|
18
|
+
const yyoffset = ox + fw * (yy + oy);
|
|
19
|
+
const yoffset = left + bw * (yy + top);
|
|
20
|
+
b32.subarray(yoffset, width + yoffset).set(f32.subarray(yyoffset, width + yyoffset));
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export function blend(bg, fg, x, y) {
|
|
25
|
+
const b32 = bg.u32;
|
|
26
|
+
const f32 = fg.u32;
|
|
27
|
+
const fw = fg.width | 0;
|
|
28
|
+
const bw = bg.width | 0;
|
|
29
|
+
const fh = fg.height | 0;
|
|
30
|
+
const bh = bg.height | 0;
|
|
31
|
+
const ox = (x > 0 ? 0 : -x) | 0;
|
|
32
|
+
const oy = (y > 0 ? 0 : -y) | 0;
|
|
33
|
+
const top = (y > 0 ? y : 0) | 0;
|
|
34
|
+
const left = (x > 0 ? x : 0) | 0;
|
|
35
|
+
const width = (Math.min(bw, x + fw) - left) | 0;
|
|
36
|
+
const height = (Math.min(bh, y + fh) - top) | 0;
|
|
37
|
+
|
|
38
|
+
if (0 >= width || 0 >= height) return;
|
|
39
|
+
|
|
40
|
+
for (let yy = 0 | 0; yy < height; yy++) {
|
|
41
|
+
const yyoffset = ox + fw * (yy + oy);
|
|
42
|
+
const yoffset = left + bw * (yy + top);
|
|
43
|
+
|
|
44
|
+
for (let xx = 0 | 0; xx < width; xx++) {
|
|
45
|
+
const F = f32[xx + yyoffset];
|
|
46
|
+
|
|
47
|
+
// todo: be?
|
|
48
|
+
const fa = F >> 24 & 0xff;
|
|
49
|
+
if (fa === 0x00) continue;
|
|
50
|
+
else if (fa === 0xff) b32[xx + yoffset] = F;
|
|
51
|
+
|
|
52
|
+
else {
|
|
53
|
+
const alpha = 1 + fa;
|
|
54
|
+
const inv_alpha = 256 - fa;
|
|
55
|
+
const B = b32[xx + yoffset];
|
|
56
|
+
const r = (alpha * (F & 0xff) + inv_alpha * (B & 0xff)) >> 8;
|
|
57
|
+
const g = (alpha * ((F >> 8) & 0xff) + inv_alpha * ((B >> 8) & 0xff)) >> 8;
|
|
58
|
+
const b = (alpha * ((F >> 16) & 0xff) + inv_alpha * ((B >> 16) & 0xff)) >> 8;
|
|
59
|
+
b32[xx + yoffset] = (Math.max(fa, (B >> 24) & 0xff) << 24) | ((b & 0xff) << 16) | ((g & 0xff) << 8) | r;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
63
|
}
|