TL;DR
พร็อพเพอร์ตี้ CSS overscroll-behavior
ช่วยให้นักพัฒนาแอปสามารถลบล้างลักษณะการเลื่อนแบบแสดงผลเกินขอบเขตเริ่มต้นของเบราว์เซอร์เมื่อถึงด้านบน/ด้านล่างของเนื้อหา กรณีการใช้งานรวมถึงการปิดใช้พุลเพื่อรีเฟรช
บนอุปกรณ์เคลื่อนที่ การลบเอฟเฟกต์การเรืองแสงและแถบยาง
รวมถึงป้องกันไม่ให้เนื้อหาในหน้าเว็บเลื่อนเมื่ออยู่ใต้โมดัล/โฆษณาซ้อนทับ
ข้อมูลเบื้องต้น
ขอบเขตการเลื่อนและโซ่การเลื่อน
การเลื่อนเป็นหนึ่งในวิธีพื้นฐานที่สุดในการโต้ตอบกับหน้าเว็บ แต่ รูปแบบ UX บางรูปแบบอาจจัดการได้ยากเพราะ พฤติกรรมที่เป็นค่าเริ่มต้น ตัวอย่างเช่น ดูตัวอย่างหน้าที่รวมแอปทั้งหมด รายการที่ผู้ใช้อาจต้องเลื่อนดู เมื่อถึงด้านล่างสุด คอนเทนเนอร์รายการเพิ่มเติมหยุดเลื่อนเนื่องจากไม่มีเนื้อหาให้บริโภคแล้ว กล่าวคือ ผู้ใช้ ถึง "ขอบเขตการเลื่อน" แต่โปรดสังเกตว่าจะเกิดอะไรขึ้นหากผู้ใช้ยังคง เลื่อน เนื้อหาด้านหลังลิ้นชักจะเริ่มเลื่อน การเลื่อนคือ ที่คอนเทนเนอร์ระดับบนสุดจะเข้ามาแทนที่ ของตัวหน้าหลักในตัวอย่าง
ปรากฏว่าลักษณะการทำงานนี้เรียกว่าการทำสายโซ่แบบเลื่อน ค่าเริ่มต้นของเบราว์เซอร์ พฤติกรรมเมื่อเลื่อนเนื้อหา บางครั้งค่าเริ่มต้นก็ดูดี แต่บางครั้งก็อาจไม่เหมาะสมหรือแม้แต่คาดไม่ถึง แอปบางแอปอาจต้องการทำสิ่งต่อไปนี้ ซึ่งจะมอบประสบการณ์การใช้งานที่แตกต่างออกไปเมื่อผู้ใช้ผ่านขอบเขตการเลื่อน
เอฟเฟกต์การดึงเพื่อรีเฟรช
ดึงเพื่อรีเฟรช คือท่าทางสัมผัสที่ใช้งานง่ายซึ่งเป็นที่นิยมในแอปบนอุปกรณ์เคลื่อนที่ เช่น Facebook และ Twitter การดึงฟีดโซเชียลลงแล้วปล่อยจะเป็นการเปิดพื้นที่ใหม่เพื่อให้ระบบโหลดโพสต์ล่าสุด อันที่จริง UX นี้มี เป็นที่นิยมอย่างมากจนเบราว์เซอร์ในอุปกรณ์เคลื่อนที่อย่าง Chrome ใน Android นำมาใช้ แบบเดียวกัน การเลื่อนลงที่ด้านบนของหน้าจะรีเฟรชทั้งหน้า ดังนี้
สำหรับสถานการณ์ต่างๆ อย่างเช่น Twitter PWA
อาจเหมาะสมที่จะปิดใช้การดำเนินการ
แบบพุลเพื่อรีเฟรชแบบเนทีฟ เหตุผล ในแอปนี้ คุณอาจไม่ต้องการให้ผู้ใช้รีเฟรชหน้าเว็บโดยไม่ตั้งใจ มี
คุณก็อาจเห็นภาพเคลื่อนไหวแบบรีเฟรช 2 ครั้งเช่นกัน หรืออาจปรับแต่งการทํางานของเบราว์เซอร์ให้สอดคล้องกับการสร้างแบรนด์ของเว็บไซต์มากขึ้น แต่ข้อเสียคือการปรับแต่งประเภทนี้ทำได้ยาก นักพัฒนาซอฟต์แวร์จึงต้องเขียน JavaScript ที่ไม่จำเป็น เพิ่ม non-passive Listeners ที่ตอบสนองต่อการสัมผัส (ซึ่งบล็อกการเลื่อน) หรือติดทั้งหน้าใน 100vw/vh<div>
(เพื่อป้องกันไม่ให้หน้าเว็บแสดงเกินขอบ) การแก้ปัญหาเหล่านี้ส่งผลเสียต่อประสิทธิภาพการเลื่อนอย่างมีเอกสารประกอบ
เราทำได้ดีกว่านี้
ขอแนะนำ overscroll-behavior
overscroll-behavior
property เป็นฟีเจอร์ CSS ใหม่ที่ควบคุมลักษณะการทํางานที่เกิดขึ้นเมื่อคุณเลื่อนคอนเทนเนอร์ (รวมถึงหน้าเว็บเอง) เกินขอบ ซึ่งคุณสามารถใช้เพื่อยกเลิกการเชื่อมโยงการเลื่อน ปิดใช้/ปรับแต่ง
การดึงเพื่อรีเฟรช ปิดใช้เอฟเฟกต์แถบยางใน iOS (เมื่อใช้ Safari
ใช้งาน overscroll-behavior
) และอื่นๆ
ที่สำคัญคือการใช้ overscroll-behavior
จะไม่ส่งผลเสียต่อประสิทธิภาพหน้าเว็บเหมือนแฮ็กที่กล่าวถึงในส่วนนําเข้า
พร็อพเพอร์ตี้ใช้ค่าที่เป็นไปได้ 3 ค่าดังนี้
- auto - ค่าเริ่มต้น การเลื่อนที่มาจากองค์ประกอบอาจส่งผลต่อองค์ประกอบหลัก
- contain - ป้องกันไม่ให้มีการเลื่อนแบบเชน การเลื่อนไม่เผยแพร่ไปยังระดับบน
แต่จะแสดงเอฟเฟ็กต์เฉพาะที่ภายในโหนด เช่น การเรืองแสงจากการเลื่อนไปจนสุด
ส่งผลต่อ Android หรือเอฟเฟกต์ยางรัดใน iOS ซึ่งจะแจ้งเตือนผู้ใช้
เมื่อถึงขอบเขตการเลื่อน หมายเหตุ: การใช้
overscroll-behavior: contain
ในองค์ประกอบhtml
ป้องกันไม่ให้เกิดการเลื่อนมากเกินไป การนำทาง - ไม่มี - เหมือนกับ
contain
แต่ป้องกันเอฟเฟกต์การเลื่อนเกินภายใน ตัวโหนดเอง (เช่น การเรืองแสงของการเลื่อนไปจนสุดของ Android หรือแถบยางของ iOS)
มาเจาะลึกตัวอย่างการใช้งาน overscroll-behavior
กัน
ป้องกันไม่ให้การเลื่อนออกจากองค์ประกอบตำแหน่งคงที่
สถานการณ์ของกล่องแชท
ลองใช้แชทบ็อกซ์ที่แสดงในตำแหน่งคงที่ซึ่งอยู่ด้านล่างของหน้า กล่าวคือช่องแชทเป็นคอมโพเนนต์ ที่ทำงานได้ด้วยตนเองและจะเลื่อน แยกจากเนื้อหาที่อยู่เบื้องหลัง แต่ด้วยห่วงโซ่การเลื่อน องค์ประกอบ เอกสารจะเริ่มเลื่อนทันทีที่ผู้ใช้แตะข้อความสุดท้ายในแชท ประวัติการเข้าชม
สำหรับแอปนี้ การมีม้วนหนังสือที่เกิดขึ้นภายใน
กล่องแชทจะอยู่แค่ในแชท เราทําเช่นนั้นได้โดยการเพิ่ม overscroll-behavior: contain
ไปยังองค์ประกอบที่เก็บข้อความแชท
#chat .msgs {
overflow: auto;
overscroll-behavior: contain;
height: 300px;
}
โดยพื้นฐานแล้ว เรากำลังจะสร้างการแบ่งแยกอย่างเป็นเหตุเป็นผลระหว่างการเลื่อนของช่องแชท บริบทและหน้าหลัก ผลลัพธ์ที่ได้คือหน้าหลักจะยังคงอยู่เมื่อผู้ใช้เลื่อนไปที่ด้านบน/ด้านล่างของประวัติการแชท การเลื่อนที่เริ่มต้นใน ช่องแชทไม่เผยแพร่
สถานการณ์การซ้อนทับหน้าเว็บ
อีกรูปแบบหนึ่งของ "underscroll" สถานการณ์สมมติเมื่อ
คุณเห็นเนื้อหา
เลื่อนลงหลังการวางซ้อนตำแหน่งคงที่ การแจกของรางวัลที่ตายแล้ว
overscroll-behavior
พร้อมใช้งานแล้ว เบราว์เซอร์พยายามช่วยเหลือ แต่กลับทำให้เว็บไซต์ดูมีข้อบกพร่อง
ตัวอย่าง - โมดัลที่มีและไม่มี overscroll-behavior: contain
กำลังปิดใช้การพุลเพื่อรีเฟรช
การปิดการดึงเพื่อรีเฟรชเป็น CSS เพียงบรรทัดเดียว เพียงป้องกัน
ห่วงโซ่การเลื่อนในองค์ประกอบที่กำหนดวิวพอร์ตทั้งหมด ในกรณีส่วนใหญ่ นั่นก็คือ
<html>
หรือ <body>
:
body {
/* Disables pull-to-refresh but allows overscroll glow effects. */
overscroll-behavior-y: contain;
}
ด้วยการเพิ่มง่ายๆ นี้ เราจึงแก้ไขภาพเคลื่อนไหวแบบดึงเพื่อรีเฟรชสองครั้งใน การสาธิตกล่องแชท และสามารถ ให้ใช้เอฟเฟกต์ที่กำหนดเองแทน ซึ่งใช้ภาพเคลื่อนไหวการโหลดที่ลื่นไหล กล่องจดหมายทั้งหมดจะเบลอเมื่อรีเฟรชกล่องจดหมาย:
ข้อมูลโค้ดตัวอย่างของโค้ดแบบเต็มมีดังนี้
<style>
body.refreshing #inbox {
filter: blur(1px);
touch-action: none; /* prevent scrolling */
}
body.refreshing .refresher {
transform: translate3d(0,150%,0) scale(1);
z-index: 1;
}
.refresher {
--refresh-width: 55px;
pointer-events: none;
width: var(--refresh-width);
height: var(--refresh-width);
border-radius: 50%;
position: absolute;
transition: all 300ms cubic-bezier(0,0,0.2,1);
will-change: transform, opacity;
...
}
</style>
<div class="refresher">
<div class="loading-bar"></div>
<div class="loading-bar"></div>
<div class="loading-bar"></div>
<div class="loading-bar"></div>
</div>
<section id="inbox"><!-- msgs --></section>
<script>
let _startY;
const inbox = document.querySelector('#inbox');
inbox.addEventListener('touchstart', e => {
_startY = e.touches[0].pageY;
}, {passive: true});
inbox.addEventListener('touchmove', e => {
const y = e.touches[0].pageY;
// Activate custom pull-to-refresh effects when at the top of the container
// and user is scrolling up.
if (document.scrollingElement.scrollTop === 0 && y > _startY &&
!document.body.classList.contains('refreshing')) {
// refresh inbox.
}
}, {passive: true});
</script>
การปิดใช้การเรืองแสงและแถบยางยืด
ในการปิดใช้เอฟเฟ็กต์การตีกลับเมื่อโดนขอบเขตการเลื่อน ให้ใช้
overscroll-behavior-y: none
:
body {
/* Disables pull-to-refresh and overscroll glow effect.
Still keeps swipe navigations. */
overscroll-behavior-y: none;
}
การสาธิตแบบเต็ม
สรุปข้อมูลทั้งหมดก็คือ
การใช้งานChatbox
overscroll-behavior
เพื่อสร้างภาพเคลื่อนไหวที่กำหนดเองแบบดึงเพื่อรีเฟรช
และปิดใช้การเลื่อนไม่ให้ Escape วิดเจ็ตช่องแชท ซึ่งจะให้ผลดีที่สุด
ประสบการณ์ของผู้ใช้คงยากที่จะบรรลุผลหากไม่มี CSS
overscroll-behavior