Scrollend เหตุการณ์ JavaScript ใหม่

ลบฟังก์ชันการหมดเวลาและกำจัดข้อบกพร่องของฟังก์ชันเหล่านั้น เหตุการณ์ที่คุณต้องการจริงๆ คือ scrollend

Adam Argyle
Adam Argyle

ก่อนเหตุการณ์ scrollend ยังไม่มีวิธีที่เชื่อถือได้ในการระบุว่าการเลื่อนสิ้นสุดแล้ว ซึ่งหมายความว่าเหตุการณ์จะทริกเกอร์ช้าหรือขณะที่นิ้วของผู้ใช้ยังอยู่บนหน้าจอ ความไม่แน่นอนในการทราบว่าการเลื่อนสิ้นสุดลงแล้วจริงๆ ทำให้ระบบเกิดข้อบกพร่องและผู้ใช้ได้รับประสบการณ์การใช้งานที่ไม่ดี

ก่อน
document.onscroll = event => {
  clearTimeout(window.scrollEndTimer)
  window.scrollEndTimer = setTimeout(callback, 100)
}

กลยุทธ์ setTimeout() นี้ทำได้ดีที่สุดคือดูว่ามีการหยุดเลื่อนหรือไม่สำหรับ 100ms ซึ่งทำให้ดูเหมือนเหตุการณ์การเลื่อนหยุดชั่วคราวมากกว่าเหตุการณ์การเลื่อนสิ้นสุด

หลังจากเหตุการณ์ scrollend เบราว์เซอร์จะประเมินสิ่งต่างๆ ที่ยากๆ ทั้งหมดนี้ให้คุณ

หลัง
document.onscrollend = event => {…}

เยี่ยมเลย กำหนดเวลาอย่างเหมาะสมและเต็มไปด้วยเงื่อนไขที่มีความหมายก่อนที่จะส่ง

การรองรับเบราว์เซอร์

  • Chrome: 114
  • Edge: 114
  • Firefox: 109
  • Safari: ไม่รองรับ

แหล่งที่มา

ลองใช้งาน

รายละเอียดเหตุการณ์

เหตุการณ์ scrollend จะทริกเกอร์ในกรณีต่อไปนี้ - เบราว์เซอร์ไม่ได้แสดงภาพเคลื่อนไหวหรือแปลการเลื่อนอีกต่อไป - ผู้ใช้ปล่อยนิ้วออกจากหน้าจอแล้ว - ผู้ใช้ปล่อยนิ้วออกจากปุ่มเลื่อน - ผู้ใช้ปล่อยการกดแป้นแล้ว - เลื่อนไปยังส่วนที่เลือกเสร็จสมบูรณ์ - เลื่อนเพื่อดูภาพเสร็จสมบูรณ์แล้ว - scrollTo() เสร็จสมบูรณ์แล้ว - ผู้ใช้เลื่อนวิวพอร์ตภาพ

เหตุการณ์ scrollend จะไม่ทริกเกอร์ในกรณีต่อไปนี้ - ท่าทางสัมผัสของผู้ใช้ไม่ได้ทําให้เกิดการเปลี่ยนแปลงตําแหน่งการเลื่อน (ไม่มีการแปลภาษา) - scrollTo() ไม่มีการแปล

สาเหตุที่กิจกรรมนี้ใช้เวลานานกว่าจะมาถึงแพลตฟอร์มเว็บเนื่องจากมีรายละเอียดเล็กๆ น้อยๆ มากมายที่ต้องระบุข้อมูลจำเพาะ หนึ่งในส่วนที่ซับซ้อนที่สุดคือการอธิบายรายละเอียด scrollend สำหรับวิดเจ็ตภาพเทียบกับเอกสาร ลองพิจารณาหน้าเว็บที่คุณซูมเข้า คุณสามารถเลื่อนไปรอบๆ เมื่ออยู่ในสถานะการซูมนี้ และไม่จำเป็นต้องเลื่อนเอกสาร โปรดมั่นใจได้ว่าการเลื่อนในวิวพอร์ตภาพซึ่งเกิดจากผู้ใช้จะส่งเหตุการณ์ scrollend เมื่อดำเนินการเสร็จสมบูรณ์

การใช้เหตุการณ์

คุณสามารถลงทะเบียน Listeners ได้ 2 วิธีเช่นเดียวกับเหตุการณ์การเลื่อนอื่นๆ

addEventListener("scrollend", (event) => {
  // scroll ended
});

aScrollingElement.addEventListener("scrollend", (event) => {
  // scroll ended
});

หรือใช้พร็อพเพอร์ตี้เหตุการณ์

document.onscrollend = (event) => {
  // scroll ended
};

aScrollingElement.onscrollend = (event) => {
  // scroll ended
};

โพลีฟิลล์และการเพิ่มประสิทธิภาพแบบต่อเนื่อง

หากคุณต้องการใช้เหตุการณ์ใหม่นี้ในตอนนี้ คำแนะนำที่ดีที่สุดของเรามีดังนี้ คุณใช้กลยุทธ์สิ้นสุดการเลื่อนปัจจุบันต่อไปได้ (หากมี) และตรวจสอบการรองรับในตอนต้นด้วยสิ่งต่อไปนี้

'onscrollend' in window
// true, if available

ซึ่งจะรายงานเป็น "จริง" หรือ "เท็จ" ขึ้นอยู่กับว่าเบราว์เซอร์เสนอเหตุการณ์หรือไม่ การตรวจสอบนี้ช่วยให้คุณแยกโค้ดได้ ดังนี้

if ('onscrollend' in window) {
  document.onscrollend = callback
}
else {
  document.onscroll = event => {
    clearTimeout(window.scrollEndTimer)
    window.scrollEndTimer = setTimeout(callback, 100)
  }
}

นี่เป็นจุดเริ่มต้นที่ดีในการปรับปรุงกิจกรรม scrollend อย่างต่อเนื่องเมื่อพร้อมใช้งาน นอกจากนี้ คุณยังลองใช้ polyfill (NPM) ที่เราสร้างขึ้นซึ่งทำงานได้ดีที่สุดเท่าที่เบราว์เซอร์จะทำได้ ดังนี้

import {scrollend} from "scrollyfills"

// then use scrollend as if it's existed this whole time
document.onscrollend = callback

โพลีฟีลจะปรับปรุงอย่างต่อเนื่องเพื่อใช้เหตุการณ์ scrollend ที่รวมอยู่ในเบราว์เซอร์ (หากมี) หากไม่มีข้อมูลนี้ สคริปต์จะคอยดูเหตุการณ์เคอร์เซอร์และเลื่อนเพื่อประมาณการสิ้นสุดเหตุการณ์ให้ใกล้เคียงที่สุด

กรณีการใช้งาน

คุณควรหลีกเลี่ยงการทำงานที่ต้องคำนวณมากขณะที่เลื่อนอยู่ แนวทางปฏิบัตินี้ช่วยให้การเลื่อนใช้หน่วยความจําและการประมวลผลได้อย่างเต็มที่เพื่อให้ประสบการณ์การใช้งานราบรื่น การใช้เหตุการณ์ scrollend ช่วยให้คุณแสดงข้อความและดึงดูดความสนใจได้เหมาะเจาะที่สุด เนื่องจากผู้ใช้ไม่ได้เลื่อนดูอีกต่อไป

คุณใช้เหตุการณ์ scrollend เพื่อทริกเกอร์การดําเนินการต่างๆ ได้ Use Case ที่พบบ่อยคือการซิงค์องค์ประกอบ UI ที่เชื่อมโยงกับตําแหน่งที่การเลื่อนหยุด เช่น - การซิงค์ตำแหน่งการเลื่อนของภาพสไลด์กับตัวบ่งชี้จุด - การซิงค์รายการแกลเลอรีกับข้อมูลเมตา - การดึงข้อมูลหลังจากที่ผู้ใช้เลื่อนไปยังแท็บใหม่

ลองนึกถึงสถานการณ์ เช่น ผู้ใช้ปัดอีเมลออก หลังจากผู้ใช้ปัดเสร็จแล้ว คุณจะดําเนินการตามตําแหน่งที่ผู้ใช้เลื่อนไป

นอกจากนี้ คุณยังใช้เหตุการณ์นี้เพื่อซิงค์หลังจากการเลื่อนแบบเป็นโปรแกรมหรือแบบผู้ใช้ หรือการดำเนินการต่างๆ เช่น การบันทึกข้อมูลวิเคราะห์ได้ด้วย

ต่อไปนี้เป็นตัวอย่างที่ดีที่องค์ประกอบหลายอย่าง เช่น ลูกศร จุด และโฟกัส ต้องอัปเดตตามตำแหน่งการเลื่อน ดูวิธีที่ฉันสร้างภาพสไลด์นี้บน YouTube นอกจากนี้ โปรดลองใช้เดโมเวอร์ชันที่ใช้จริง

ขอขอบคุณ Mehdi Kazemi สำหรับงานด้านวิศวกรรมเกี่ยวกับเรื่องนี้ และ Robert Flack สำหรับคำแนะนำเกี่ยวกับ API และการใช้งาน