เหมือนกับการค้นหาคอนเทนเนอร์ แต่สําหรับการค้นหาที่ค้างอยู่ หยุดชะงัก และล้น
เผยแพร่: 15 ม.ค. 2025
Chrome 133 พัฒนาจากการค้นหาคอนเทนเนอร์ด้วยการแสดงการค้นหาคอนเทนเนอร์สถานะการเลื่อน ตอนนี้คุณสามารถค้นหาและปรับสถานะที่จัดการโดยเบราว์เซอร์สำหรับตำแหน่งที่ยึด ตำแหน่งที่เลื่อนไปหยุดเอง และองค์ประกอบที่เลื่อนได้จาก CSS แล้ว
ภาพรวม
ก่อนที่จะทำการค้นหาสถานะการเลื่อน คุณต้องใช้ JavaScript เพื่อดูว่าองค์ประกอบค้าง หยุดอยู่ที่จุดใดจุดหนึ่ง หรือเลื่อนได้หรือไม่ ตอนนี้เรามีวิธีการที่มีประสิทธิภาพมากขึ้นในแทร็กมาตรฐานในการดูข้อมูลนี้และปรับเปลี่ยนตามความเหมาะสม นอกจากนี้ยังมีวิธีใหม่ในการเรียกให้ภาพเคลื่อนไหวแสดง ซึ่งจะปลดล็อกภาพเคลื่อนไหวที่เรียกให้แสดงเมื่อเลื่อนจาก CSS
ภาพรวมของการค้นหาสถานะที่พร้อมใช้งานใน Chrome 133 มีดังนี้
- สถานะค้าง
- ทริกเกอร์การเปลี่ยนแปลงสไตล์เมื่อองค์ประกอบติดอยู่ที่ขอบ
- สถานะรวม:
- รูปแบบทริกเกอร์จะเปลี่ยนเมื่อองค์ประกอบมีการปักหมุดบนแกน
- สถานะเลื่อนได้
- ทริกเกอร์การเปลี่ยนแปลงรูปแบบเมื่อองค์ประกอบแสดงเกินขอบ
ข่าวดีคือทุกสิ่งที่คุณได้เรียนรู้จากคําค้นหาคอนเทนเนอร์จะช่วยคุณทํางานกับคําค้นหาสถานะการเลื่อน
นอกจากนี้ ยังมีอีกเรื่องหนึ่งที่ยังไม่เป็นที่ทราบแน่ชัดระหว่างภาพเคลื่อนไหวที่ทำงานตามการเลื่อนกับการค้นหาคอนเทนเนอร์สถานะการเลื่อน เราจําเป็นต้องทดสอบจังหวะและบริบทเพื่อค้นหาว่าภาพเคลื่อนไหวที่ทำงานตามการเลื่อนหรือภาพเคลื่อนไหวสถานะการเลื่อนที่ทริกเกอร์โดยการเลื่อนจะเหมาะที่สุด วิดีโอและเดโมต่อไปนี้แสดงปัญหาที่เกิดขึ้นเมื่อเปรียบเทียบภาพเคลื่อนไหวที่ทริกเกอร์แบบติดหนึบกับภาพเคลื่อนไหวที่ทำงานเมื่อเลื่อน
การค้นหาสถานะการเลื่อนครั้งแรก
ขั้นตอนแรกคือกําหนดคอนเทนเนอร์โดยใช้ค่าใหม่สําหรับพร็อพเพอร์ตี้ container-type
เช่นเดียวกับการค้นหาคอนเทนเนอร์ องค์ประกอบที่คุณต้องการค้นหาคือองค์ประกอบที่คุณให้ container-type
และ container-name
(ไม่บังคับ) เมื่อใช้การค้นหาสถานะการเลื่อน คุณจะระบุcontainer-type: scroll-state
ให้กับองค์ประกอบที่ยึด ติด หรือมีการแสดงผลเกิน
.stuck-top {
container-type: scroll-state;
position: sticky;
top: 0px;
}
ขั้นตอนที่ 2 คือเลือกรายการย่อยของคอนเทนเนอร์ที่จะตอบสนองต่อสถานะ เช่นเดียวกับการค้นหาคอนเทนเนอร์ รายการนี้ต้องไม่ใช่องค์ประกอบเดียวกันที่มี container-type
.stuck-top {
container-type: scroll-state;
position: sticky;
top: 0px;
> nav {
@container scroll-state(stuck: top) {
background: Highlight;
color: HighlightText;
}
}
}
ขั้นตอนที่ 3 คือลองใช้ ตัวอย่าง CSS ต่อไปนี้จะจัดรูปแบบพื้นหลังเป็นสีแดงเมื่อองค์ประกอบ .stuck-top
ติดอยู่ที่ด้านบนที่ 0
การเพิ่มบรรทัด CSS 2-3 บรรทัดที่เราควรจะเขียนไว้แล้วและองค์ประกอบที่มีเพิ่มเติมซึ่งทำหน้าที่เป็นพร็อกซีสถานะเบราว์เซอร์ ทําให้คอมโพเนนต์ของเราฉลาดขึ้นมากเกี่ยวกับสภาพแวดล้อมรอบตัว
การเพิ่มประสิทธิภาพแบบต่อเนื่อง
@supports
at-rule และการฝังช่วยให้คุณเพิ่มการเพิ่มประสิทธิภาพแบบเป็นขั้นเป็นตอนหรือการใช้ฟีเจอร์แบบมีเงื่อนไขได้โดยใช้โค้ดเพียง 2-3 บรรทัด ดังนี้
.stuck-top {
container-type: scroll-state;
position: sticky;
top: 0px;
@supports (container-type: scroll-state) {
> nav {
@container scroll-state(stuck: top) {
background: Highlight;
color: HighlightText;
}
}
}
}
นอกจากนี้ อย่าลืมใช้ @media (prefers-reduced-motion: no-preference) {}
กับการเคลื่อนไหวด้วย หากคุณทำให้องค์ประกอบในหน้าเว็บเคลื่อนไหวด้วยการค้นหาสถานะการเลื่อน
กรณีการใช้งาน
ติดค้าง
เราควรตั้งชื่อส่วนนี้ว่า "สถานการณ์ที่แก้ไขยาก" ไหม นี่เป็นคอลเล็กชันเล็กๆ ของกรณีการใช้งานสถานะที่ติดหนึบ รวมถึงส่วนเสริมของไอเดียที่ต้องสร้าง
@container scroll-state(stuck: top) {}
@container scroll-state(stuck: bottom) {}
เพิ่มเงาเมื่อติดอยู่
Use Case ที่พบบ่อยที่สุดอย่างหนึ่งสำหรับคำค้นหาที่ค้างคือแถบนําทางที่ต้องการเพิ่ม box-shadow
เมื่อค้าง เพื่อให้ดูเหมือนว่าลอยอยู่เหนือเนื้อหาที่วางซ้อน
.stuck-top {
container-type: scroll-state;
position: sticky;
top: 0px;
> nav {
transition: box-shadow .3s ease;
@container scroll-state(stuck: top) {
box-shadow: var(--shadow-5);
}
}
}
เปิดใช้งานส่วนหัวที่ค้างอยู่ในปัจจุบัน
อีกสถานการณ์ที่พบบ่อยของความคิดเห็นเกี่ยวกับ UI ที่ติดอยู่คือการไฮไลต์องค์ประกอบที่ค้างอยู่ ในรายการวงดนตรีที่จัดเรียงตามลำดับตัวอักษร ฟีเจอร์นี้มีประโยชน์และช่วยเสริมประสบการณ์การใช้งานได้เป็นอย่างมาก
.sticky-slide {
dt {
container-type: scroll-state;
position: sticky;
inset-block-start: 0;
inset-inline: 0;
> header {
transition:
background .3s ease,
box-shadow .5s ease;
@container scroll-state(stuck: top) {
background: hsl(265 100% 27%);
box-shadow: 0 5px 5px #0003;
}
}
}
}
นี่เป็นรูปแบบอื่นที่ส่วนหัวอยู่ด้านข้างรายการในลิสต์ เป็นไปได้หลายอย่าง
ไอเดียที่แสดงเกิน
ต่อไปนี้เป็นรายการเดโมแบบติดหนึบซึ่งอาจสร้างแรงบันดาลใจให้คุณเพิ่มลูกเล่นเล็กๆ น้อยๆ ลงในเดโม หรือนํา JavaScript ออกด้วยการค้นหาสถานะการเลื่อน เราขอแนะนำให้ลองสร้างแบบที่คุณชอบ ซึ่งจะช่วยให้คุณจดจำไวยากรณ์และแนวคิดต่างๆ ได้ดีขึ้น 😏
- https://codepen.io/BlogFire/pen/PoGMjaX - ตัวแปรโน้ตติดหนึบ
- https://codepen.io/mikegolus/pen/jOZzRzw - เพิ่มเงาให้กับตารางเมื่อติดอยู่
- https://codepen.io/MarcRay/pen/PomBeP - แถบนาบาร์ปรากฏขึ้นเมื่อมีการทริกเกอร์ในส่วนหัว
- https://codepen.io/kevinpowell/pen/OqKJjK - การแสดงแถบนําทางด้านท้าย
- https://codepen.io/abhisekz-the-decoder/pen/eKaLRd - ส่วนหัวของการ์ดแบบติดหนึบ
- https://codepen.io/tutsplus/pen/abojPjP - การใช้เงาในส่วนหัวราคาบนทริกเกอร์
- https://codepen.io/kevinpowell/pen/KEjMEv - ชื่อแถบด้านข้างของส่วนแบบติดหนึบ
รวมรูปถ่าย
การใช้การค้นหาสถานะแบบยึดตำแหน่งช่วยให้เรานำภาระหน้าที่บางอย่างออกจาก JavaScript และ Snap Events และย้ายการจัดการไปยัง CSS ได้
@container scroll-state(snapped: x) {}
@container scroll-state(snapped: y) {}
@container scroll-state(snapped: inline) {}
@container scroll-state(snapped: block) {}
โปรดทราบว่าในกรณีที่คุณข้ามส่วนการค้นหาสถานะการเลื่อนครั้งแรก คอนเทนเนอร์สําหรับการค้นหาแบบ Snap คือองค์ประกอบที่มี scroll-snap-align
และองค์ประกอบที่ปรับได้ต้องเป็นองค์ประกอบย่อยขององค์ประกอบนั้น ซึ่งหมายความว่าคุณจะต้องมีองค์ประกอบ 3 อย่างในการตั้งค่านี้ ได้แก่
a scroll container with `scroll-snap-type`
⤷ a snap target with both `scroll-snap-align` and `container-type: scroll-state`
⤷ a child of the snap target that can query the container for snap state
เพิ่มขนาดของรายการที่จับภาพ
การใช้แถบเลื่อนที่ปักหมุดไว้ตรงกลางเพื่อไฮไลต์หรือแสดงรายการที่ปักหมุดไว้ตรงกลางนั้นเป็นเรื่องปกติ ในตัวอย่างนี้ของข้อความรับรอง มีการใช้คีย์เวิร์ด not
เพื่อให้ข้อความรับรองทั้งหมดที่ไม่ได้แสดงผลแบบสแน็ปมีความทึบแสงต่ำ ส่วนข้อความรับรองที่แสดงผลแบบสแน็ปจะอยู่ในสถานะการแสดงผลตามปกติ
.demo {
overflow: auto hidden;
scroll-snap-type: x mandatory;
> article {
container-type: scroll-state;
scroll-snap-align: center;
@supports (container-type: scroll-state) {
> * {
transition: opacity .5s ease;
@container not scroll-state(snapped: x) {
opacity: .25;
}
}
}
}
}
แสดงคำบรรยายสำหรับรายการที่จับภาพ
นี่เป็นตัวอย่างที่ดีที่แสดงให้เห็นว่าการค้นหาสถานะการเลื่อนช่วยให้ภาพเคลื่อนไหวที่ทริกเกอร์ด้วยการเลื่อนทำงานได้อย่างไร และยังถือเป็นตัวอย่างที่ดีว่าเมื่อใดการลดการเคลื่อนไหวจะมีประโยชน์ใน CSS
.demo {
overflow-x: auto;
scroll-behavior-x: contain;
scroll-snap-type: x mandatory;
> .card {
container-type: scroll-state;
scroll-snap-align: center;
@supports (container-type: scroll-state) {
@media (prefers-reduced-motion: no-preference) {
figcaption {
transform: translateY(100%);
@container scroll-state(snapped: x) {
transform: translateY(0);
}
}
}
}
}
}
การทำองค์ประกอบในสไลด์เคลื่อนไหว
การใช้ภาพเคลื่อนไหวกับองค์ประกอบของภาพสไลด์หรืองานนำเสนอขณะบรรยายนั้นเป็นเรื่องปกติ ก่อนหน้านี้การเขียน IntersectionObserver สำหรับการดำเนินการนี้ค่อนข้างน่ารำคาญ เนื่องจากสิ่งที่ทำได้มีเพียงการตั้งค่าคลาสในสไลด์ ตอนนี้เราไม่จำเป็นต้องใช้ JavaScript เลย
html {
scroll-snap-type: y mandatory;
}
section {
container-type: scroll-state;
scroll-snap-align: start;
scroll-snap-stop: always;
@supports (container-type: scroll-state) {
@media (prefers-reduced-motion: no-preference) {
> h1 {
transition: opacity .5s ease, transform .5s var(--ease-spring-3);
transition-delay: .5s;
opacity: 0;
transform: scale(1.25);
@container scroll-state(snapped: block) {
opacity: 1;
transform: scale(1);
}
}
}
}
}
คุณอาจสังเกตเห็นว่าการค้นหาสถานะ CSS ที่จับภาพไว้ทั้งหมดทํางานเหมือน scrollsnapchanging
แทนที่จะเป็น scrollsnapchange
ซึ่งจะช่วยให้คุณมีจุดเริ่มต้นที่เร็วที่สุดในการให้ฟีดแบ็กภาพเกี่ยวกับองค์ประกอบที่ปักหมุดไว้ หากการเรียกใช้เกิดขึ้นเร็วเกินไป ให้ลองใช้เหตุการณ์ JavaScript
เลื่อนได้
การค้นหาสถานะ "เลื่อนได้" จะมีประโยชน์อย่างมากในการแสดงสิ่งต่างๆ ที่มองเห็นได้เมื่อพื้นที่เลื่อนสามารถเลื่อนได้จริง ก่อนหน้านี้ ข้อมูลนี้ถือเป็นข้อมูลที่ทราบได้ยาก
@container scroll-state(scrollable: top) {}
@container scroll-state(scrollable: right) {}
@container scroll-state(scrollable: bottom) {}
@container scroll-state(scrollable: left) {}
ระบุการเลื่อนด้วยเงา
มีเคล็ดลับ CSS โดย Lea Verou ที่โด่งดังซึ่งใช้ background-attachment: local
เพื่อให้ได้เอฟเฟกต์ที่คล้ายกับนี้ รวมถึงวิธีทำด้วยภาพเคลื่อนไหวที่ทำงานตามการเลื่อน เทคนิคแต่ละอย่างมีข้อดีข้อเสียต่างกันไป เราจึงต้องหาว่าเทคนิคแต่ละอย่างเหมาะกับสถานการณ์ใดและเมื่อใด
ตัวอย่างต่อไปนี้ใช้องค์ประกอบที่ติดอยู่รายการเดียวที่ครอบคลุมพื้นที่การเลื่อน ไล่ระดับสีที่ด้านบนและไล่ระดับสีที่ด้านล่างมีการแสดงผลระดับทึบเป็นภาพเคลื่อนไหวด้วย @property
เมื่อการค้นหาสถานะการเลื่อนตามบริบทมีผล: @container scroll-state(scrollable: top)
และโปรดทราบว่านี่เป็นคอนเทนเนอร์แรกที่เป็นทั้งคอนเทนเนอร์ size
และ scroll-state
.scroll-container {
container-type: scroll-state size;
overflow: auto;
&::after {
content: " ";
background: var(--_shadow-top), var(--_shadow-bottom);
transition:
--_scroll-shadow-color-1-opacity .5s ease,
--_scroll-shadow-color-2-opacity .5s ease;
@container scroll-state(scrollable: top) {
--_scroll-shadow-color-1-opacity: var(--_shadow-color-opacity, 25%);
}
@container scroll-state(scrollable: bottom) {
--_scroll-shadow-color-2-opacity: var(--_shadow-color-opacity, 25%);
}
}
}
พรอมต์ลูกศร
บางครั้งการแสดงลูกศรอาจช่วยให้ผู้ใช้ทราบว่าพื้นที่หนึ่งๆ เลื่อนได้ โดยมักจะชี้ไปในทิศทางที่การเลื่อนอาจเกิดขึ้น และหายไปเมื่อไม่จําเป็นต้องใช้แล้ว ซึ่งทำได้โดยใช้โค้ดต่อไปนี้
@container scroll-state((scrollable: top) or (not (scrollable: bottom))) {
translate: 0 calc(100% + 10px);
}
@container scroll-state((scrollable: top) and (not (scrollable: bottom))) {
translate: 0 calc(100% + 10px);
rotate: .5turn;
}
กลับไปด้านบน
การโต้ตอบกับสถานะการเลื่อนอีกอย่างหนึ่งที่ได้รับความนิยมคือปุ่ม "เลื่อนขึ้นด้านบน" โค้ดต่อไปนี้จะทำให้ปุ่มเลื่อนขึ้นด้านบนหายไปเมื่อไม่มีที่เลื่อนขึ้น
โซลูชันนี้อาจดูย้อนแย้งไปหน่อย แต่จะช่วยให้คุณลดจำนวน CSS ได้ ปุ่มควรอยู่ในมุมมองตามปกติ คุณจึงต้องบอกให้ปุ่มซ่อนตัวเมื่อเลื่อนขึ้นไม่ไหวแล้ว
@container not scroll-state(scrollable: top) {
translate: 0 calc(100% + 10px);
}
การศึกษาต่อเนื่อง
หากต้องการข้อมูลเพิ่มเติม โปรดดูแหล่งข้อมูลต่อไปนี้ซึ่งมีตั้งแต่รายละเอียดข้อกำหนดทางเทคนิคไปจนถึงบทความอื่นๆ ที่ยอดเยี่ยมซึ่งครอบคลุมหัวข้อนี้
- มีอะไรอีกไหมที่เราควรค้นหาในคอนเทนเนอร์ได้ https://github.com/w3c/csswg-drafts/issues/5989
- คําอธิบาย scroll-state() - https://drafts.csswg.org/css-conditional-5/scroll_state_explainer.md
- ข้อกำหนด CSS ของ scroll-state() - https://www.w3.org/TR/css-conditional-5/#scroll-state-container
- การจับภาพเลย์เอาต์ในลูปเหตุการณ์ HTML
- ตอนของพอดแคสต์เกี่ยวกับคําค้นหาสถานะ - https://nerdy.dev/the-css-podcast-on-state-queries
- บทความเพิ่มเติม
- https://utilitybend.com/blog/is-the-sticky-thing-stuck-is-the-snappy-item-snapped-a-look-at-state-queries-in-css/
- https://ishadeed.com/article/css-state-queries/
- https://csscade.com/can-you-detect-overflow-with-css/
- https://css-tip.com/overflow-detection/ - การตรวจหาด้วยภาพเคลื่อนไหวที่ทำงานด้วยการปัดในลักษณะที่ผู้ใช้ทั่วไปสามารถรับรู้ได้ (โดยต้องแลกมาด้วยการใช้กลโกง)