|
15 | 15 |
|
16 | 16 | import {
|
17 | 17 | assert,
|
| 18 | + FeatureTest, |
18 | 19 | FormatError,
|
19 | 20 | info,
|
20 | 21 | shadow,
|
@@ -60,6 +61,61 @@ function resizeRgbImage(src, dest, w1, h1, w2, h2, alpha01) {
|
60 | 61 | }
|
61 | 62 | }
|
62 | 63 |
|
| 64 | +function resizeRgbaImage(src, dest, w1, h1, w2, h2, alpha01) { |
| 65 | + const xRatio = w1 / w2; |
| 66 | + const yRatio = h1 / h2; |
| 67 | + let newIndex = 0; |
| 68 | + const xScaled = new Uint16Array(w2); |
| 69 | + |
| 70 | + if (alpha01 === 1) { |
| 71 | + for (let i = 0; i < w2; i++) { |
| 72 | + xScaled[i] = Math.floor(i * xRatio); |
| 73 | + } |
| 74 | + const src32 = new Uint32Array(src.buffer); |
| 75 | + const dest32 = new Uint32Array(dest.buffer); |
| 76 | + const rgbMask = FeatureTest.isLittleEndian ? 0x00ffffff : 0xffffff00; |
| 77 | + for (let i = 0; i < h2; i++) { |
| 78 | + const buf = src32.subarray(Math.floor(i * yRatio) * w1); |
| 79 | + for (let j = 0; j < w2; j++) { |
| 80 | + dest32[newIndex++] |= buf[xScaled[j]] & rgbMask; |
| 81 | + } |
| 82 | + } |
| 83 | + } else { |
| 84 | + const COMPONENTS = 4; |
| 85 | + const w1Scanline = w1 * COMPONENTS; |
| 86 | + for (let i = 0; i < w2; i++) { |
| 87 | + xScaled[i] = Math.floor(i * xRatio) * COMPONENTS; |
| 88 | + } |
| 89 | + for (let i = 0; i < h2; i++) { |
| 90 | + const buf = src.subarray(Math.floor(i * yRatio) * w1Scanline); |
| 91 | + for (let j = 0; j < w2; j++) { |
| 92 | + const oldIndex = xScaled[j]; |
| 93 | + dest[newIndex++] = buf[oldIndex]; |
| 94 | + dest[newIndex++] = buf[oldIndex + 1]; |
| 95 | + dest[newIndex++] = buf[oldIndex + 2]; |
| 96 | + } |
| 97 | + } |
| 98 | + } |
| 99 | +} |
| 100 | + |
| 101 | +function copyRgbaImage(src, dest, alpha01) { |
| 102 | + if (alpha01 === 1) { |
| 103 | + const src32 = new Uint32Array(src.buffer); |
| 104 | + const dest32 = new Uint32Array(dest.buffer); |
| 105 | + const rgbMask = FeatureTest.isLittleEndian ? 0x00ffffff : 0xffffff00; |
| 106 | + for (let i = 0, ii = src32.length; i < ii; i++) { |
| 107 | + dest32[i] |= src32[i] & rgbMask; |
| 108 | + } |
| 109 | + } else { |
| 110 | + let j = 0; |
| 111 | + for (let i = 0, ii = src.length; i < ii; i += 4) { |
| 112 | + dest[j++] = src[i]; |
| 113 | + dest[j++] = src[i + 1]; |
| 114 | + dest[j++] = src[i + 2]; |
| 115 | + } |
| 116 | + } |
| 117 | +} |
| 118 | + |
63 | 119 | class ColorSpace {
|
64 | 120 | constructor(name, numComps) {
|
65 | 121 | if (
|
@@ -806,6 +862,32 @@ class DeviceRgbaCS extends ColorSpace {
|
806 | 862 | isPassthrough(bits) {
|
807 | 863 | return bits === 8;
|
808 | 864 | }
|
| 865 | + |
| 866 | + fillRgb( |
| 867 | + dest, |
| 868 | + originalWidth, |
| 869 | + originalHeight, |
| 870 | + width, |
| 871 | + height, |
| 872 | + actualHeight, |
| 873 | + bpc, |
| 874 | + comps, |
| 875 | + alpha01 |
| 876 | + ) { |
| 877 | + if (originalHeight !== height || originalWidth !== width) { |
| 878 | + resizeRgbaImage( |
| 879 | + comps, |
| 880 | + dest, |
| 881 | + originalWidth, |
| 882 | + originalHeight, |
| 883 | + width, |
| 884 | + height, |
| 885 | + alpha01 |
| 886 | + ); |
| 887 | + } else { |
| 888 | + copyRgbaImage(comps, dest, alpha01); |
| 889 | + } |
| 890 | + } |
809 | 891 | }
|
810 | 892 |
|
811 | 893 | /**
|
|
0 commit comments