| <!DOCTYPE html> |
| <head> |
| <title>Images with loading='lazy' load only when in the viewport</title> |
| <link rel="author" title="Dom Farolino" href="mailto:dom@chromium.org"> |
| <link rel="author" title="Scott Little" href="mailto:sclittle@chromium.org"> |
| <link rel="help" href="https://github.com/scott-little/lazyload"> |
| <script src="/resources/testharness.js"></script> |
| <script src="/resources/testharnessreport.js"></script> |
| </head> |
| |
| <script> |
| const in_viewport_test = |
| async_test("In-viewport loading=lazy images load immediately but do not " + |
| "block the window load event"); |
| const below_viewport_test = |
| async_test("Below-viewport loading=lazy images only load when in the " + |
| "viewport and do not block the window load event"); |
| const below_viewport_data_url_test = |
| async_test("Below-viewport data:url images only load when in the " + |
| "viewport and do not block the window load event"); |
| const below_viewport_blob_url_test = |
| async_test("Below-viewport blob URL images only load when in the " + |
| "viewport and do not block the window load event"); |
| |
| document.addEventListener('DOMContentLoaded', e => { |
| const img = document.querySelector('#below_viewport_blob_url'); |
| |
| // Blob URL helper. |
| // Source: https://bl.ocks.org/nolanlawson/0eac306e4dac2114c752. |
| function fixBinary(bin) { |
| const length = bin.length; |
| const buf = new ArrayBuffer(length); |
| const arr = new Uint8Array(buf); |
| for (var i = 0; i < length; i++) { |
| arr[i] = bin.charCodeAt(i); |
| } |
| |
| return buf; |
| } |
| |
| const base64 = |
| "R0lGODlhDAAMAKIFAF5LAP/zxAAAANyuAP/gaP///wAAAAAAACH5BAEAAAUALAAAAAAMAAwAAAMlWLPcGjDKFYi9lxKBOaGcF35DhWHamZUW0K4mAbiwWtuf0uxFAgA"; |
| const binary = fixBinary(atob(base64)); |
| const blob = new Blob([binary], {type: 'image/png'}); |
| const url = URL.createObjectURL(blob); |
| img.src = url; |
| }) // DOMContentLoaded. |
| |
| let has_window_load_fired = false; |
| let has_in_viewport_loaded = false; |
| |
| window.onload = e => { |
| has_window_load_fired = true; |
| } |
| |
| // Helper assertion messages for the below tests. |
| const kScrollAssertion = "images only load when scrolled into view"; |
| const kWindowLoadAssertion = "images do not block the load event"; |
| |
| const in_viewport_img_onload = in_viewport_test.step_func_done(() => { |
| has_in_viewport_loaded = true; |
| document.querySelector('#bottom').scrollIntoView(); |
| assert_true(has_window_load_fired, |
| "In-viewport loading=lazy images do not block the window " + |
| "load event"); |
| }); |
| |
| const below_viewport_img_onload = below_viewport_test.step_func_done(() => { |
| assert_true(has_in_viewport_loaded, |
| "Below-viewport loading=lazy images only load once loaded " + |
| "into the viewport"); |
| assert_true(has_window_load_fired, |
| "Below-viewport loading=lazy images should not block the " + |
| "window load event"); |
| }); |
| |
| const below_viewport_data_url_img_onload = below_viewport_data_url_test.step_func_done(() => { |
| assert_true(has_in_viewport_loaded, |
| "Below-viewport loading=lazy data: url images " + |
| kScrollAssertion); |
| assert_true(has_window_load_fired, |
| "Below-viewport loading=lazy data: url images " + |
| kWindowLoadAssertion); |
| }); |
| |
| const below_viewport_blob_url_img_onload = below_viewport_blob_url_test.step_func_done(() => { |
| assert_true(has_in_viewport_loaded, |
| "Below-viewport loading=lazy blob url images " + |
| kScrollAssertion); |
| assert_true(has_window_load_fired, |
| "Below-viewport loading=lazy blob url images " + |
| kWindowLoadAssertion); |
| }); |
| </script> |
| |
| <body> |
| <!-- |in_viewport| takes 2 seconds to load, so that in browsers that don't |
| support lazy loading, |below_viewport| finishes before |in_viewport|, and |
| the test will dependably fail without relying on a timeout. --> |
| <img id="in_viewport" loading="lazy" src="resources/image.png?first&pipe=trickle(d2)" |
| onload="in_viewport_img_onload()"> |
| <div style="height:1000vh;"></div> |
| <img id="below_viewport" loading="lazy" src="resources/image.png?second" |
| onload="below_viewport_img_onload()"> |
| <img id="below_viewport_data_url" loading="lazy" |
| src="data:image/png;base64,R0lGODlhDAAMAKIFAF5LAP/zxAAAANyuAP/gaP///wAAAAAAACH5BAEAAAUALAAAAAAMAAwAAAMlWLPcGjDKFYi9lxKBOaGcF35DhWHamZUW0K4mAbiwWtuf0uxFAgA" |
| onload="below_viewport_data_url_img_onload()"> |
| <!-- This image has its `src` set to a blob URL dynamically above --> |
| <img id="below_viewport_blob_url" loading="lazy" |
| onload="below_viewport_blob_url_img_onload()"> |
| <div id="bottom"></div> |
| </body> |