摘要:主要用于元素可見性的監(jiān)聽,比傳統(tǒng)通過全局監(jiān)聽事件去判斷可見性無論是性能還是便利性都要好得多。問題是這種通過監(jiān)聽的方式很容易導(dǎo)致性能問題,或者多多少少會(huì)有些性能損失。
IntersectionObserver主要用于元素可見性的監(jiān)聽,比傳統(tǒng)通過全局監(jiān)聽scroll事件去判斷可見性無論是性能還是便利性都要好得多。因?yàn)閍pi比較新,存在兼容性問題,好在已經(jīng)有了兼容的polyfill.其基本介紹和使用方式都可以在該polyfill對(duì)應(yīng)網(wǎng)站上看到。這里主要通過例子的形式,說明其實(shí)用的場景。
圖片懶加載 之前的方式以前我們實(shí)現(xiàn)圖片懶加載的原理是這樣的:
window.addEventListener("scroll", lazyload); function lazyload() { const imgs = document.querySelector(".img"); const innerHeight = util.innerHeight(); const scrollTop = util.scrollTop(); imgs.forEach((img) => { const imgOffsetH = util.getPosition(img).top; // 距離頁面頂部的距離 <= 視窗高 + 往上滾進(jìn)去的距離 if(imgOffsetH <= innerHeight + scrollTop) { img.src = img.getAttribute("data-src"); } }) }
條件是:距離頁面頂部的距離 <= 視窗高 + 往上滾進(jìn)去的距離,即算做圖片可見了才加載它。問題是這種通過監(jiān)聽scroll的方式很容易導(dǎo)致性能問題,或者多多少少會(huì)有些性能損失。
IntersectionObserver的方式const io = new IntersectionObserver((entrys) => { entrys.forEach((img) => { if(!img.isIntersecting) return; img.src = img.getAttribute("data-src"); io.unobserve(img); }) }, { //即滾動(dòng)到距離底部50px時(shí)開始算交互區(qū) rootMargin:"0px 0px 50px 0px" }) imgs.forEach((img) => { io.observe(img); })
非常的清晰和簡單,而且由于是原生的功能,不會(huì)引起性能損耗。這里的rootMargin參數(shù)非常好用,因?yàn)橐话闱闆r下的交互條件都需要添加一定的閾值,以實(shí)現(xiàn)更優(yōu)雅和流暢的體驗(yàn),而通過rootMargin能非常簡單的實(shí)現(xiàn)這點(diǎn)。
完整示例請(qǐng)參考lazyload.html滾動(dòng)分頁 以前的方式
通過判斷滾動(dòng)是否到底部,即 視窗高+往上滾進(jìn)去的距離>= 頁面高,來作為加載新的一頁的條件:
window.addEventListener("scroll", () => { const innerHeight = util.innerHeight(); const scrollTop = util.scrollTop(); const scrollHeight = util.scrollHeight(); // 滾動(dòng)到距離底部50px if(innerHeight + scrollTop >= scrollHeight - 50) { loadMore(); } });IntersectionObserver的方式
在最底部設(shè)置一個(gè)加載更多的標(biāo)記器,監(jiān)聽它是否出現(xiàn),作為加載新頁的條件:
const io = new IntersectionObserver((entrys) => { entrys.forEach((entry) => { if(!entry.isIntersecting) return; loadMore(); }) }, { rootMargin:"0px 0px 50px 0px" }) //監(jiān)聽最底部的loadmore是否出現(xiàn) const lMore = document.querySelector(".load-more"); io.observe(lMore);
在性能上仍然更勝一籌,而且不必每次都去判斷視窗高、滾進(jìn)去的距離等等,將以往很麻煩的事情變得簡單而快捷。
完整示例請(qǐng)參考paging.html
通過上面的兩個(gè)例子,基本能了解IntersectionObserver的功能實(shí)用場景,即監(jiān)聽元素的出現(xiàn),實(shí)現(xiàn)懶加載(可以是圖片、模版、甚至組件等等)、元素進(jìn)出動(dòng)畫、分頁等各種形式的功能。這對(duì)優(yōu)化整個(gè)頁面的性能還是非常有幫助的,所以在日常的項(xiàng)目中還是很值得嘗試。
本文收錄在個(gè)人的Github上https://github.com/kekobin/bl... ,覺得有幫助的,歡迎start哈。支持原創(chuàng),未經(jīng)本人同意,請(qǐng)勿轉(zhuǎn)載!
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/105176.html
摘要:一掛在上的上最常用的只有其中,永遠(yuǎn)都是窗口的大小,跟隨窗口變化而變化。這個(gè)是距該元素最近的不為的祖先元素,如果沒有則指向元素。 在Javascript的開發(fā)過程中,我們總會(huì)看到類似如下的邊界條件判斷(懶加載): const scrollTop = document.documentElement.scrollTop || window.pageYOffset || document.b...
摘要:配置項(xiàng)配置項(xiàng)中的參數(shù)有以下三個(gè)所監(jiān)聽對(duì)象的具體祖先元素,默認(rèn)是計(jì)算交叉狀態(tài)時(shí),將附加到祖先元素上,從而有效的擴(kuò)大或者縮小祖先元素判定區(qū)域設(shè)置一系列的閾值,當(dāng)交叉狀態(tài)達(dá)到閾值時(shí),會(huì)觸發(fā)回調(diào)函數(shù)。 一、前言 ??通常情況下,HTML 中的圖片資源會(huì)自上而下依次加載,而部分圖片只有在用戶向下滾動(dòng)頁面的場景下才能被看見,否則這部分圖片的流量就白白浪費(fèi)了。 ??所以,對(duì)于那些含有大量圖片資源的網(wǎng)...
摘要:同時(shí),懶加載按需加載概念至關(guān)重要。時(shí)至今日,這些實(shí)現(xiàn)懶加載腳本的代碼仍有學(xué)習(xí)意義。代碼實(shí)戰(zhàn)下面讓我們動(dòng)手實(shí)現(xiàn)一個(gè)按需加載輪子。同樣,對(duì)于組件也可以使用無狀態(tài)組件函數(shù)式組件實(shí)現(xiàn)這樣無疑更加簡潔。 組件化在當(dāng)今前端開發(fā)領(lǐng)域中是一個(gè)非常重要的概念。著名的前端類庫,比如 React、Vue 等對(duì)此概念都倍加推崇。確實(shí),組件化復(fù)用性(reusability)和模塊性(modularization...
摘要:同時(shí),懶加載按需加載概念至關(guān)重要。時(shí)至今日,這些實(shí)現(xiàn)懶加載腳本的代碼仍有學(xué)習(xí)意義。代碼實(shí)戰(zhàn)下面讓我們動(dòng)手實(shí)現(xiàn)一個(gè)按需加載輪子。同樣,對(duì)于組件也可以使用無狀態(tài)組件函數(shù)式組件實(shí)現(xiàn)這樣無疑更加簡潔。 組件化在當(dāng)今前端開發(fā)領(lǐng)域中是一個(gè)非常重要的概念。著名的前端類庫,比如 React、Vue 等對(duì)此概念都倍加推崇。確實(shí),組件化復(fù)用性(reusability)和模塊性(modularization...
閱讀 2968·2021-11-24 09:38
閱讀 3540·2021-11-23 09:51
閱讀 1030·2021-09-09 11:52
閱讀 4081·2021-08-11 11:18
閱讀 1144·2019-08-30 14:05
閱讀 3255·2019-08-30 11:23
閱讀 1796·2019-08-29 17:02
閱讀 1155·2019-08-26 13:49