NEW 241402
Decoded image data is not reused by canvas causing long task blocking on the main thread
https://bugs.webkit.org/show_bug.cgi?id=241402
Summary Decoded image data is not reused by canvas causing long task blocking on the ...
Xidorn Quan
Reported 2022-06-07 22:04:13 PDT
Created attachment 460082 [details] testcase STR: 1. download the attachment and serve it and open it 2. click the button in the page Expected result: The decoding takes sometime, but drawing is instant, and there is no long task detected on the main thread. Actual result: Both the decoding and the drawing takes roughly the same amount of time, and there is a long task indicates the main thread is blocked. Seemingly that the drawing the image on canvas then `getImageData` forces a decoding of the image even if the image is already decoded through `img.decode()`. It makes it hard to avoid a long task on main thread when dealing with large images. Blink has similar issue: https://bugs.chromium.org/p/chromium/issues/detail?id=1334448 On Gecko, I get the expected result.
Attachments
testcase (45.21 KB, application/zip)
2022-06-07 22:04 PDT, Xidorn Quan
no flags
Radar WebKit Bug Importer
Comment 1 2022-06-14 22:05:13 PDT
Kimmo Kinnunen
Comment 2 2022-08-15 23:52:04 PDT
Thanks for the test-case! For WebKit internals: The long duration after initial decode() is due to the way WP transfers the data to GPUP the first time. The new NativeImage gets sent over to GPUP during this duration. There are at least 3 different undesirable behaviors in WebKit: 1. initial draw after decode() is slow 2. Multiple .src assignments and decode()s are slow for same url. 3. Big getImageData() is slow (10ms on WebKit, ~0ms on Firefox)
Thomas Steiner
Comment 3 2022-10-20 06:14:01 PDT
See https://bugs.chromium.org/p/chromium/issues/detail?id=1334448#c9 for a hosted demo and https://bugs.chromium.org/p/chromium/issues/detail?id=1334448#c10 for a theory of why the seemingly double decoding might happen.
Xidorn Quan
Comment 4 2022-11-15 13:06:36 PST
Thomas suggested to us that for this testcase, we can set `image.decoding` to `async`, and that seems to help on Chrome (where `draw` call is now immediate most of time), but not on Safari.
Xidorn Quan
Comment 5 2022-11-15 13:34:05 PST
No, I was wrong. It didn't help on Chrome either. Chrome was to some extent cheating by somehow reusing a decoded image from a previous image load. If I randomize the URL by adding `?` with `Math.random()` to the end of the URL, double decoding happens every time again.
Note You need to log in before you can comment on or make changes to this bug.