unrelated-gesture-scroll-during-snap.html (5382B)
1 <!DOCTYPE html> 2 <html> 3 <head> 4 <link rel="help" href="https://drafts.csswg.org/css-scroll-snap-1" /> 5 <script src="/resources/testharness.js"></script> 6 <script src="/resources/testharnessreport.js"></script> 7 <script src="/resources/testdriver.js"></script> 8 <script src="/resources/testdriver-actions.js"></script> 9 <script src="/resources/testdriver-vendor.js"></script> 10 <script src="/dom/events/scrolling/scroll_support.js"></script> 11 <script src="support/common.js"></script> 12 </head> 13 <body> 14 <style> 15 .scroller { 16 border: solid 1px black; 17 overflow-y: scroll; 18 height: 200px; 19 width: 200px; 20 display: inline-block; 21 background-color: yellow; 22 position: relative; 23 } 24 .snapcontainer { 25 scroll-snap-type: y mandatory; 26 } 27 .snaparea { 28 scroll-snap-align: start; 29 margin-bottom: 120%; 30 height: 40px; 31 width: 50px; 32 background-color: green; 33 } 34 .space { 35 height: 500vh; 36 width: 500vw; 37 position: absolute; 38 } 39 </style> 40 <div> 41 <div id="plaincontainer" class="scroller"> 42 <div class="snaparea"></div> 43 <div class="snaparea"></div> 44 <div class="snaparea"></div> 45 <div class="snaparea"></div> 46 <div class="snaparea"></div> 47 </div> 48 <div id="snapcontainer1" class="scroller snapcontainer"> 49 <div class="snaparea"></div> 50 <div class="snaparea"></div> 51 <div class="snaparea"></div> 52 <div class="snaparea"></div> 53 <div class="snaparea"></div> 54 </div> 55 <div id="snapcontainer2" class="scroller snapcontainer"> 56 <div class="snaparea"></div> 57 <div class="snaparea"></div> 58 <div class="snaparea"></div> 59 <div class="snaparea"></div> 60 <div class="snaparea"></div> 61 </div> 62 </div> 63 <script> 64 const plaincontainer = document.getElementById("plaincontainer"); 65 const snapcontainer1 = document.getElementById("snapcontainer1"); 66 const snapcontainer2 = document.getElementById("snapcontainer2"); 67 68 async function test_unrelated_gesture_during_snap(t, 69 snapcontainer, 70 other_container, 71 inputs, 72 expectations) { 73 await waitForScrollReset(t, snapcontainer); 74 await waitForScrollReset(t, other_container); 75 await waitForCompositorCommit(); 76 77 assert_equals(snapcontainer.scrollTop, 0, "snapcontainer is reset."); 78 assert_equals(other_container.scrollTop, 0, `${other_container.id} is ` + 79 `reset.`); 80 const scrollend_promises = [ 81 waitForScrollendEventNoTimeout(snapcontainer), 82 waitForScrollendEventNoTimeout(other_container) 83 ]; 84 let last_scroll_top = snapcontainer.scrollTop; 85 async function scroll_listener() { 86 // If we are scrolling back to 0, we are snapping. 87 if (snapcontainer.scrollTop < last_scroll_top) { 88 snapcontainer.removeEventListener("scroll", scroll_listener); 89 await new test_driver.Actions().scroll(0, 0, 0, inputs.scroll_amt, 90 { origin: other_container }).send(); 91 } 92 last_scroll_top = snapcontainer.scrollTop; 93 } 94 snapcontainer.addEventListener("scroll", scroll_listener); 95 96 // The snap areas are separated by margin-bottom: 120%. Scrolling to 97 // almost halfway should snap back to 0. 98 const snap_scroll_amt = snapcontainer.clientHeight / 2; 99 await new test_driver.Actions().scroll(0, 0, 0, snap_scroll_amt, 100 { origin: snapcontainer }) 101 .send(); 102 103 await Promise.all(scrollend_promises); 104 assert_equals(snapcontainer.scrollTop, 0, 105 "snapcontainer snaps back to 0"); 106 assert_equals(other_container.scrollTop, expectations.expectedScrollTop, 107 `${other_container.id} is at expected scroll offset.`); 108 } 109 110 promise_test(async (t) => { 111 await test_unrelated_gesture_during_snap(t, snapcontainer1, 112 plaincontainer, 113 { scroll_amt: 100 }, 114 { expectedScrollTop: 100 }); 115 }, "gesture on separate scroll container works while another container "+ 116 "snaps"); 117 118 promise_test(async (t) => { 119 // scrolling the full clientHeight of snapcontainer2 should result in 120 // snapping to its second snap area. 121 const scroll_amt = snapcontainer2.clientHeight; 122 const expectedScrollTop = snapcontainer2.querySelectorAll(".snaparea")[1].offsetTop; 123 await test_unrelated_gesture_during_snap(t, snapcontainer1, 124 snapcontainer2, 125 { scroll_amt: scroll_amt }, 126 { expectedScrollTop: expectedScrollTop}); 127 }, "gesture on separate snap container works while another container "+ 128 "snaps"); 129 </script> 130 </body> 131 </html>