You need to wait for the image to load before you draw, otherwise you’re likely not to get anything. Just as I was writing this answer, someone else posted code that’ll put you on the right track, it just needs to be modified a bit to handle the onload function as a Promise if you want to stick to the async function paradigm.
Update: Here’s the code in async form:
showData = async (url, x, y) => {
let image_ = document.getElementById("map_image")
image_.crossOrigin = "Anonymous"
await new Promise((resolve, reject) => {
image_.onload = () => resolve()
image_.onerror = err => reject(err)
})
let canvas = document.createElement('canvas');
let context = canvas.getContext('2d');
context.drawImage(image_, 0, 0, 100, 100)
// No await here -- this method is synchronous
let data = context.getImageData(0, 0, 50, 50).data
console.log(data)
}
Solution 2 :
Please try this:
showData = (url, x, y) => {
let image_ = document.getElementById('map_image')
image_.crossOrigin = 'Anonymous'
let canvas = document.createElement('canvas');
let context = canvas.getContext('2d');
return Promise((resolve) => {
image_.onLoad = () => {
context.drawImage(image_, 0, 0, 100, 100);
let data = context.getImageData(0, 0, 50, 50).data;
console.log(data);
resolve(data);
};
});
};
(Code modified per kshetline’s suggestion to support returning the data via promise.)
Problem :
Working on a react component where I have the following in my render():
this.state.last_parking.url is simply some url I’m saving in my local state.
I want the value of the rgba colors in this image. So I made a function like this which uses my img element through id map_image:
showData = async (url, x, y) => {
let image_ = document.getElementById("map_image")
image_.crossOrigin = "Anonymous"
let canvas = document.createElement('canvas');
let context = canvas.getContext('2d');
context.drawImage(image_, 0, 0, 100, 100)
let data = await context.getImageData(0, 0, 50, 50).data
console.log(data)
}
Unfortunately, what I see in the console is some sort of Uint8ClampedArray where every single value is 0. Honestly, I just want the rgba values in the very center of the image. How can I make my getImageData array have actual rgba values?
Yes, OK so both of your codes, after some minor modification for my particular circumstances, work fine. I guess the central idea I was missing was using asynchronous Promise based technique on getImageData. That was actually the whole issue. I think I’ve got to review how to implement Promises to force synchronous behavior for this and future issues. Thanks a ton!
Comment posted by see sharper
You’re welcome – upvote and/or mark as answer appreciated.
Comment posted by Mahdiur Rahman
I can’t 🙁 my reputation is too low. I upvoted both of you guys it just won’t show.