-
Notifications
You must be signed in to change notification settings - Fork 151
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[TypeScript] Quantization of relatively large images doesn't work in Chrome #130
Labels
explain
(Label used internally)
Comments
@rodydavis @guidezpl Could you please take a look? 😉 |
@pennzht @marshallworks PTAL. |
why not modify existing buffer? const _forEach = (tarray, cb) => tarray.forEach(cb) ?? tarray;
return _forEach(new Uint32Array(data.buffer), (abgr, index, tarray) =>
tarray.set([abgr & 0xFF00FF00 | (abgr & 255) << 16 | abgr >> 16 & 255], index)); ..or map new return new Uint32Array(data.buffer).map((abgr) =>
abgr & 0xFF00FF00 | (abgr & 255) << 16 | abgr >> 16 & 255); |
Working sample tested with Chromium <html>
<body>
<script type="module">
import { QuantizerCelebi, Score } from 'https://unpkg.com/@material/material-color-utilities';
const image = new Image();
image.crossOrigin = 'Anonymous';
image.src = 'https://r4.wallpaperflare.com/wallpaper/727/861/207/spiderman-ps4-spiderman-games-hd-wallpaper-2460826541419b3727663083655888cf.jpg';
async function sourceColorFromImage(image) {
const imageBytes = await new Promise((resolve, reject) => {
const canvas = document.createElement('canvas');
const context = canvas.getContext('2d');
if (!context) {
reject(new Error('Could not get canvas context'));
return;
}
const callback = () => {
canvas.width = image.width;
canvas.height = image.height;
context.drawImage(image, 0, 0);
let rect = [0, 0, image.width, image.height];
const area = image.dataset['area'];
if (area && /^\d+(\s*,\s*\d+){3}$/.test(area)) {
rect = area.split(/\s*,\s*/).map(s => {
// tslint:disable-next-line:ban
return parseInt(s, 10);
});
}
const [sx, sy, sw, sh] = rect;
resolve(context.getImageData(sx, sy, sw, sh).data);
};
if (image.complete) {
callback();
}
else {
image.onload = callback;
}
});
const bufferArray = new Uint32Array(imageBytes.buffer);
bufferArray.forEach((abgr, index, tarray) =>
tarray.set([abgr & 0xFF00FF00 | (abgr & 255) << 16 | abgr >> 16 & 255], index));
const result = QuantizerCelebi.quantize(bufferArray, 128);
const ranked = Score.score(result);
const top = ranked[0];
return top;
}
const sourceColor = await sourceColorFromImage(image);
console.log('sourceColor', sourceColor);
</script>
</body>
</html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Quantization of images that contains >= 50139473 pixels doesn't work in Chrome.
Tested in Chrome x64 on Windows.
Not reproducible in Firefox.
This means e.g. an image with a resolution of 7080x7080 px can still be quantized, but 7081x7081 px cannot.
Minimal repro:
Error:
Code line:
material-color-utilities/typescript/utils/image_utils.ts
Line 71 in f5d03da
As far as I know, JavaScript arrays are zero-based and use 32-bit indexes: the index of the first element is 0, and the highest possible index is 4294967294 (2^32−2), for a maximum array size of 4,294,967,295 elements. Not 50,139,473. :)
The text was updated successfully, but these errors were encountered: