ใช้แนวทางแบบอิงเวลาในการทำแอนิเมชัน CSS
- เมื่อ CSS รองรับฟังก์ชันทางคณิตศาสตร์แล้ว จึงสามารถนำแนวทางแอนิเมชัน CSS แบบอิงเวลาไปทดลองใช้งานได้อีกครั้ง
- รองรับ
mod(), round() และฟังก์ชันตรีโกณมิติ
- อาจต้องเปิดใช้งานฟีเจอร์ทดลองเพื่อดูเดโม
แนวคิดหลัก
- สามารถกำหนดตัวแปรที่กำหนดเองเพื่อติดตามเวลา (มิลลิวินาที) ได้ด้วย CSS Houdini API
- ใช้กฎ
@property ในการกำหนดตัวแปร --t และตั้งค่าเริ่มต้นเป็น 0
- ใช้กฎ
@keyframes ให้ตัวแปร --t เพิ่มขึ้นแบบเชิงเส้นตลอด 24 ชั่วโมง (86,400,000ms)
- ค่าต่าง ๆ ที่อิงจาก
--t จะเปลี่ยนไปพร้อมกัน ทำให้เกิดเอฟเฟกต์แอนิเมชัน
- ใช้ฟังก์ชัน
counter() เพื่อแสดงค่าของตัวแปร --t
การควบคุมอัตราเฟรม
- การคงความถี่การอัปเดตที่ 60 เฟรมต่อวินาที (FPS) ถือว่าพอเพียงสำหรับแอนิเมชันที่ลื่น
- หากจำเป็น สามารถควบคุมอัตราเฟรมด้วยตนเองด้วยฟังก์ชัน
step() ได้
- ใช้ฟังก์ชัน
step() ในคุณสมบัติ animation-timing-function เพื่อคำนวณค่า FPS ที่ต้องการ
การแปลงเวลา
- เนื่องจากค่า
--t เพิ่มขึ้นแบบทางเดียวอย่างต่อเนื่อง จึงอาจไม่เหมาะกับคุณสมบัติของ CSS บางตัว
- ใช้
min() เพื่อหยุดแอนิเมชันเมื่อถึงค่าเป้าหมาย
- ใช้
mod() เพื่อสตาร์ทแอนิเมชันใหม่
- ใช้
sin() เพื่อสร้างเอฟเฟกต์การเคลื่อนไหวไป-กลับ
ฟังก์ชัน Easing แบบกำหนดเอง
- ใช้ฟังก์ชันทางคณิตศาสตร์และตัวแปร
--t เพื่อสร้างฟังก์ชัน easing แบบกำหนดเอง
- สามารถสร้างเอฟเฟกต์ที่ทำได้ยากด้วย
cubic-bezier()
- ตัวอย่างเช่น ease-out-cubic, ease-out-elastic และอื่น ๆ
การทดลองด้วย CSS Doodle
- ในนิพจน์ที่ซับซ้อน
var() และ calc() อาจทำให้โค้ดอ่านยากขึ้น
- ใน
css-doodle สามารถแทนตัวแปร --t โดยใช้ฟังก์ชัน @t
- เวอร์ชันล่าสุดของ
css-doodle อนุญาตให้ใส่นิพจน์คณิตศาสตร์แบบง่าย ๆ โดยตรงในอาร์กิวเมนต์
- นอกจากนี้ยังมีฟังก์ชัน
@T และ @TS ให้ใช้งานด้วย
@T แสดงเวลาตั้งแต่เริ่มต้นวัน
@TS เป็นรูปย่อของ @t(/1000) ซึ่งใช้ติดตามเวลาเป็นวินาที
- สามารถสร้างตัวอย่างนาฬิกาและตัวอย่างการกระโดดด้วย
css-doodle ได้
สรุป
- แนวทางนี้ที่ใช้ตัวแปรแทนเวลาเป็นศูนย์กลางนั้นน่าสนใจ
- แม้การใช้ Keyframes อาจจะตรงไปตรงมามากกว่า แต่สำหรับฉากตัวอย่างที่มีการคำนวณทางคณิตศาสตร์และตัวแปรอินพุตจำนวนมาก การใช้ตัวแปรเวลาอาจทำให้ได้ผลลัพธ์ที่หลากหลายมากขึ้น
ความคิดเห็นของ GN⁺
- เทคนิคแอนิเมชัน CSS แบบอิงเวลาไม่ได้เพียงขยายขอบเขตของแอนิเมชันที่ทำได้ด้วย CSS เท่านั้น แต่ยังช่วยเพิ่มโอกาสในการต่อยอดร่วมกับเทคโนโลยีอื่น เช่น shader หรือ WebGL
- หากใช้ร่วมกับเครื่องมืออย่าง CSS Houdini และ CSS Doodle การแสดงออกอาจยืดหยุ่นและหลากหลายมากขึ้น
- อย่างไรก็ตาม ปัจจัยอย่างความเข้ากันได้ของเบราว์เซอร์และประเด็นประสิทธิภาพยังต้องพิจารณาเมื่อใช้งานจริงในโปรเจกต์ ควรเปรียบเทียบข้อดีข้อเสียของแนวทาง Keyframe แบบเดิมกับแนวทางนี้อย่างรอบคอบเพื่อเลือกใช้อย่างเหมาะสม
- ควรมีการวิเคราะห์ข้อดีข้อเสียเมื่อเปรียบเทียบกับไลบรารีแอนิเมชันมืออาชีพอย่าง GSAP และควรหาทางใช้ร่วมกันแบบเสริมกันด้วย
- คาดหวังว่าจะมีตัวอย่างและกรณีใช้งานของแอนิเมชัน CSS แบบอิงเวลาเผยแพร่มากขึ้น เพื่อให้นักพัฒนาหน้าบ้านสามารถนำไปประยุกต์ได้ง่ายขึ้น
1 ความคิดเห็น
ความคิดเห็นบน Hacker News
ใช้ค่า
animation-delayแบบลบใน CSS เพื่อควบคุมความคืบหน้าแอนิเมชันด้วย JavaScript ได้ ตัวอย่างเช่น กำหนดเป็นanimation-delay: -1500msจะเริ่มเล่นทันทีแต่ข้ามไปที่จุดที่เกิดขึ้นหลัง 1.5 วินาที โดยใช้ JavaScript ควบคุมค่านี้เพื่อสกรับ (scrub) แอนิเมชัน CSS และทำให้แอนิเมชันทั้งหมดทำงานได้เข้ากับลูป tick แบบคำนวณ-อัปเดต-เรนเดอร์ตามสไตล์เกมเอนจินเมื่อเกินกว่าฟังก์ชัน
easingแบบง่าย ๆ หรือคีย์เฟรมพื้นฐานเพียงหนึ่งถึงสองช่องทาง วิธีนี้ก็จะชนขีดจำกัดเร็วมาก ใช้ไลบรารี Theatre.js ซึ่งมี UI สตูดิโอที่มีไทม์ไลน์สำหรับแก้ไขคีย์เฟรมและโค้งเบซิเยร์ และมี runtime สำหรับนำคีย์เฟรมเหล่านั้นมาแปลงค่าตามไทม์ไลน์ ซึ่งมีประโยชน์เมื่อคุณต้องการปรับแต่งแอนิเมชันบทความนี้ใช้ CSS
@propertyแบบกำหนดเองที่มีการรองรับในเบราว์เซอร์ 88% ต้องระวังว่าการตั้งค่าค่าเริ่มต้นจะแตกต่างกันตามแต่ละเบราว์เซอร์ Chrome จะใช้ค่าเริ่มต้นเมื่อค่าที่กำหนดไม่ถูกต้องหรือไม่ถูกกำหนด ในขณะที่ Firefox ใช้เฉพาะเมื่อไม่มีการกำหนดเท่านั้น โครงการส่วนใหญ่จะไม่เป็นปัญหา แต่เพื่อแก้ความไม่ตรงกันในการใช้งานระหว่างเบราว์เซอร์ อาจต้องตั้งค่าเริ่มต้นของ Firefox ผ่าน JavaScriptCSS รองรับฟังก์ชันคณิตศาสตร์ได้เพียงพอแล้ว เช่น
mod(),round(), ฟังก์ชันตรีโกณมิติ เป็นต้น CSS เองไม่สามารถเริ่มตัวจับเวลาตามแบบ JavaScript ได้ แต่ปัจจุบันด้วย CSS Houdini API ก็สามารถกำหนดตัวแปรที่ผู้ใช้กำหนดเองเพื่อจับเวลาหน่วยมิลลิวินาทีได้ แล้วคำถามคือเมื่อมี JavaScript อยู่แล้ว ทำไมจึงต้องมีสิ่งเหล่านี้ทั้งหมด? ชั้นการวาดควรมีแต่ primitive ของการวาดเท่านั้นหรือ? แล้วทำไมเราถึงต้องเพิ่มชั้นระดับสูงมากขึ้นเรื่อย ๆนาฬิกาที่ทำไว้ดูมีความหรูหรามาก เขียนได้ดีมาก บทความนี้ชัดเจนดีมาก ส่วน Chrome ยังคงไม่ปล่อยการรองรับ CSS สำหรับ
mod()ในการอัปเดตปกติ ดังนั้นหากไม่ใช้เบต้า/เวอร์ชันตัวอย่าง ส่วนใหญ่ของตัวอย่างในหน้านี้จะไม่ทำงานแอนิเมชันถ้าต้องการให้แอนิเมชัน CSS ลื่นไหลในทุกเบราว์เซอร์โดยไม่ต้องควบคุม tick เอง วิธี FLIP จะมีประโยชน์มาก
ผมอยากได้แบบฝึกหัด ‘การหายใจแบบกล่อง’ ที่ปรับขั้นหายใจเข้า-หยุด-หายใจออก-หยุด ให้เหมาะกับตัวเองและได้ผลลัพธ์ตามใจ แต่หาแนวทางอย่างที่มีบนหน้านี้ไม่ออก หากไม่อยากใช้ JS หรือความซับซ้อนมหาศาล และหน้านี้ก็มีเดโมที่สร้างสรรค์จริง ๆ
น่าสนใจมากว่าเดโมที่ใช้ก่อนหน้า
mod()ถึงแม้ยังทำงาน แต่เมื่อใช้mod()และsin()ร่วมกันบน Chrome Android รุ่นใหม่ล่าสุดก็แทบไม่ทำงานแอนิเมชันที่ด้านล่างของหน้าเป็นไปได้ยิ่งดีมาก มันดูไม่เหมือน
แต่ดูเหมือนเป็นน่าประทับใจมาก แต่ดูเหมือนเราใกล้พรมแดนที่ย้อนกลับไปสู่สิ่งที่ทำได้ด้วย Flash เมื่อหลายสิบปีก่อนแล้ว สมัยที่ Flash หายไปแล้ว แต่ก็อยากเห็นเครื่องมือที่เป็นมิตรกับผู้ใช้มากขึ้นสำหรับการสร้างแอนิเมชัน CSS มากขึ้น