นอกจากนี้ คุณยังโหลดวิดีโอแบบ Lazy Loading ได้เช่นเดียวกับองค์ประกอบรูปภาพ วิดีโอมักจะโหลดด้วยเอลิเมนต์ <video>
(แต่มีทางเลือกอื่นในการใช้ <img>
ซึ่งเกิดขึ้นใหม่ซึ่งมีการใช้งานที่จำกัด) อย่างไรก็ตาม วิธีโหลด <video>
แบบ Lazy Loading จะขึ้นอยู่กับกรณีการใช้งาน เราลองมาดู 2 สถานการณ์ที่แต่ละสถานการณ์ต้องการโซลูชันที่แตกต่างกันกัน
สำหรับวิดีโอที่ไม่เล่นอัตโนมัติ
สำหรับวิดีโอที่ผู้ใช้เป็นผู้เริ่มต้นการเล่น (กล่าวคือ วิดีโอที่ไม่ได้เล่นอัตโนมัติ) การระบุแอตทริบิวต์ preload
ในองค์ประกอบ <video>
สามารถทำได้ดังนี้
<video controls preload="none" poster="one-does-not-simply-placeholder.jpg">
<source src="one-does-not-simply.webm" type="video/webm">
<source src="one-does-not-simply.mp4" type="video/mp4">
</video>
ตัวอย่างด้านบนใช้แอตทริบิวต์ preload
ที่มีค่า none
เพื่อป้องกันไม่ให้เบราว์เซอร์โหลดข้อมูลวิดีโอใดๆ ไว้ล่วงหน้า แอตทริบิวต์ poster
ให้ตัวยึดตำแหน่งแก่องค์ประกอบ <video>
ที่จะใช้พื้นที่ขณะโหลดวิดีโอ สาเหตุก็คือลักษณะการทำงานเริ่มต้นในการโหลดวิดีโออาจแตกต่างกันไปตามแต่ละเบราว์เซอร์ ดังนี้
- ใน Chrome ค่าเริ่มต้นของ
preload
คือauto
แต่ใน Chrome 64 จะมีค่าเริ่มต้นเป็นmetadata
อย่างไรก็ตาม ใน Chrome เวอร์ชันเดสก์ท็อป ระบบอาจโหลดวิดีโอบางส่วนไว้ล่วงหน้าโดยใช้ส่วนหัวContent-Range
เบราว์เซอร์อื่นๆ ที่ใช้ Chromium และ Firefox จะทำงานในลักษณะเดียวกัน - Safari เวอร์ชัน 11.0 บนเดสก์ท็อปจะโหลดวิดีโอล่วงหน้าเช่นเดียวกับ Chrome บนเดสก์ท็อป จากเวอร์ชัน 11.2 ระบบจะโหลดเฉพาะข้อมูลเมตาของวิดีโอล่วงหน้าเท่านั้น ใน Safari บน iOS ระบบจะไม่โหลดวิดีโอไว้ล่วงหน้า
- เมื่อเปิดใช้โหมดประหยัดอินเทอร์เน็ต
preload
จะมีค่าเริ่มต้นเป็นnone
เนื่องจากลักษณะการทำงานเริ่มต้นของเบราว์เซอร์ที่เกี่ยวข้องกับ preload
ไม่ได้กำหนดไว้เป็นมาตรฐาน การใช้คำที่ไม่เหมาะสมจึงน่าจะดีที่สุด ในกรณีที่ผู้ใช้เริ่มเล่น การใช้ preload="none"
จะเป็นวิธีที่ง่ายที่สุดในการเลื่อนการโหลดวิดีโอออกไปทุกแพลตฟอร์ม แอตทริบิวต์ preload
ไม่ใช่วิธีเดียวในการเลื่อนเวลาโหลดเนื้อหาวิดีโอ การเล่นอย่างรวดเร็วด้วยการโหลดวิดีโอล่วงหน้าอาจให้แนวคิดและข้อมูลเชิงลึกบางประการเกี่ยวกับการใช้งานการเล่นวิดีโอใน JavaScript
อย่างไรก็ตาม เทมเพลตนี้อาจไม่มีประโยชน์เมื่อคุณต้องการใช้วิดีโอแทน GIF แบบเคลื่อนไหว ซึ่งจะกล่าวถึงในลำดับถัดไป
สำหรับวิดีโอที่ทำหน้าที่เป็นการแทนที่ GIF แบบเคลื่อนไหว
แม้ว่า GIF แบบเคลื่อนไหวจะใช้งานได้ในวงกว้าง แต่ก็มีประสิทธิภาพเหนือกว่าวิดีโอเทียบเท่าในหลายๆ ด้าน โดยเฉพาะในเรื่องขนาดไฟล์ GIF แบบเคลื่อนไหวสามารถขยาย ให้ครอบคลุมข้อมูลหลายเมกะไบต์ วิดีโอที่มีคุณภาพของภาพคล้ายกัน มักจะมีขนาดเล็กกว่ามาก
การใช้องค์ประกอบ <video>
เพื่อแทนที่ GIF แบบเคลื่อนไหวจะไม่ตรงไปตรงมาเท่าองค์ประกอบ <img>
GIF แบบเคลื่อนไหวมีลักษณะ 3 ประการ ดังนี้
- จะเล่นโดยอัตโนมัติเมื่อโหลดเสร็จ
- โดยจะแสดงวนซ้ำอย่างต่อเนื่อง (แต่ก็ไม่ได้เป็นเช่นนั้นเสมอไป)
- อุปกรณ์ไม่มีแทร็กเสียง
การรับค่านี้ด้วยองค์ประกอบ <video>
จะมีลักษณะดังนี้
<video autoplay muted loop playsinline>
<source src="one-does-not-simply.webm" type="video/webm">
<source src="one-does-not-simply.mp4" type="video/mp4">
</video>
แอตทริบิวต์ autoplay
, muted
และ loop
มีลักษณะที่ชัดเจนในตัวเอง
playsinline
จำเป็นสำหรับการเล่นอัตโนมัติใน iOS ตอนนี้คุณมีการเปลี่ยนวิดีโอเป็น GIF ที่ให้บริการได้ ซึ่งทำงานข้ามแพลตฟอร์มได้ แต่จะพูดถึงการโหลด
แบบ Lazy Loading ได้อย่างไร หากต้องการเริ่มต้น ให้แก้ไขมาร์กอัป <video>
ตามขั้นตอนต่อไปนี้
<video class="lazy" autoplay muted loop playsinline width="610" height="254" poster="one-does-not-simply.jpg">
<source data-src="one-does-not-simply.webm" type="video/webm">
<source data-src="one-does-not-simply.mp4" type="video/mp4">
</video>
คุณจะเห็นการเพิ่มแอตทริบิวต์ poster
ซึ่งช่วยให้คุณระบุตัวยึดตำแหน่งเพื่อใช้พื้นที่ขององค์ประกอบ <video>
ได้จนกว่าวิดีโอจะโหลดแบบ Lazy Loading เช่นเดียวกับตัวอย่างการโหลดแบบ Lazy Loading <img>
ให้เก็บ URL ของวิดีโอไว้ในแอตทริบิวต์ data-src
ในองค์ประกอบ <source>
แต่ละรายการ จากนั้นใช้โค้ด JavaScript ที่คล้ายคลึงกับตัวอย่างการโหลดรูปภาพแบบ Lazy Loading ที่อิงตาม Intersection Observer ดังนี้
document.addEventListener("DOMContentLoaded", function() {
var lazyVideos = [].slice.call(document.querySelectorAll("video.lazy"));
if ("IntersectionObserver" in window) {
var lazyVideoObserver = new IntersectionObserver(function(entries, observer) {
entries.forEach(function(video) {
if (video.isIntersecting) {
for (var source in video.target.children) {
var videoSource = video.target.children[source];
if (typeof videoSource.tagName === "string" && videoSource.tagName === "SOURCE") {
videoSource.src = videoSource.dataset.src;
}
}
video.target.load();
video.target.classList.remove("lazy");
lazyVideoObserver.unobserve(video.target);
}
});
});
lazyVideos.forEach(function(lazyVideo) {
lazyVideoObserver.observe(lazyVideo);
});
}
});
เมื่อโหลดองค์ประกอบ <video>
แบบ Lazy Loading คุณจะต้องดำเนินการซ้ำผ่านองค์ประกอบย่อย <source>
ทั้งหมดและเปลี่ยนแอตทริบิวต์ data-src
เป็นแอตทริบิวต์ src
เมื่อเสร็จแล้ว คุณต้องทริกเกอร์การโหลดวิดีโอโดยเรียกใช้เมธอด load
ขององค์ประกอบ หลังจากนั้นสื่อจะเริ่มเล่นโดยอัตโนมัติตามแอตทริบิวต์ autoplay
วิธีนี้ทำให้คุณมีโซลูชันวิดีโอที่จำลองลักษณะการทำงานของ GIF แบบเคลื่อนไหว แต่ไม่ก่อให้เกิดปริมาณการใช้อินเทอร์เน็ตมากเท่ากับที่ GIF แบบเคลื่อนไหวมี และคุณสามารถโหลดเนื้อหานั้นแบบ Lazy Loading ได้
ไลบรารีการโหลดแบบ Lazy Loading
ไลบรารีต่อไปนี้สามารถช่วยคุณโหลดวิดีโอแบบ Lazy Loading ได้
- vanilla-lazyload และ lozad.js เป็นตัวเลือกที่ใช้งานง่ายมาก ซึ่งใช้ Intersection Observer เท่านั้น ถึงแม้ว่าแท็กจะมีประสิทธิภาพสูง แต่ก็จะต้องใส่ Polyfill ก่อน จึงจะใช้กับเบราว์เซอร์รุ่นเก่าได้
- yall.js เป็นไลบรารีที่ใช้ Intersection Observer และกลับไปใช้ตัวแฮนเดิลเหตุการณ์ ทั้งยังโหลดรูปภาพวิดีโอ
poster
แบบ Lazy Loading โดยใช้แอตทริบิวต์data-poster
ได้ด้วย - หากต้องการใช้ไลบรารีการโหลดแบบ Lazy Loading ที่เจาะจงของ React คุณอาจลองใช้ react-lazyload แม้จะไม่ได้ใช้ Intersection Observer แต่ได้ให้วิธีการที่คุ้นเคยของการโหลดรูปภาพแบบ Lazy Loading สำหรับผู้ที่คุ้นเคยกับการพัฒนาแอปพลิเคชันด้วย React
ไลบรารีการโหลดแบบ Lazy Loading แต่ละไลบรารีเหล่านี้ได้รับการจัดทำเอกสารไว้อย่างดี พร้อมด้วยรูปแบบมาร์กอัปมากมายสำหรับความพยายามในการโหลดแบบ Lazy Loading แบบต่างๆ