監測元素resize

前言

近來有需求要作分頁,聽起來可能有點Low。 因此我要把Low的事情作得有點逼格。
分頁自己沒啥,可是數據量起來了,好比十萬。 要是不作點處理, 那你的頁面估計爽得很,機器也爽得很。 放心,我不會讓你這麼爽。javascript

大量數據展示方案

比較流行的固然是虛擬滾動(無限滾動)。html

  1. 始終展現的是有限的固定節點。
  2. 外層建立滾動層。

一句話,就是反覆利用固定節點展示數據。java

其中還有兩個點react

什麼時候須要加載新的分頁數據git

  1. scrollTop , clientHeight, scrollHeight
  2. IntersectionObserver (chrome 55+)

如何知道容器寬高變化
本文就圍繞着這個展開github

由於使用的是react框架,使用了 react-window, react-window就是用來展示海量數據的react列表組件。
由於項目須要,還要不通尺寸一行展示不一樣數量的數據。 確定有人就說,監聽window.resize。
chrome



沒錯,監聽resize必定程度,可是window.resize, 並不能讓我知道容器自己的尺寸,當
然能夠經過getComputedStyle獲取。 要是window沒有resize的狀況呢。


我就想實時的知道尺寸的變化。

尺寸變化監測方案

監測元素resize這裏有幾種方案的測試和源碼。框架

Cross-Browser, Event-based, Element Resize Detection

思路:函數

若是IE,直接註冊onresize(這個點贊啊)測試

不然: 建立 type爲text/html的object

設置position爲absolute, 高度100%, 寬度100% (這樣能夠得到父容器的寬高)

設置pointer-events:none,利用點擊穿透(讓object窗體變成幽靈)

object元素的高度變化後,通知訂閱者

resize事件節流

問題:

  1. 建立object
  2. 事件處理函數掛載了元素自己上

javascript-detect-element-resize

建立三個子元素,利用scroll事件來監測變化。

原理:

https://zhuanlan.zhihu.com/p/24887312
The scroll event is fired when the document view or an element has been scrolled.
當文檔視圖或者元素滾動的時候會觸發 scroll 事件。
也就是說元素滾動的時候會觸發這個事件,那麼何時元素會滾動?當元素大於其父級元素,且父級元素容許其滾動的時候,該元素能夠進行滾動。
換句話說,元素能夠滾動意味着父子元素大小不一致,這是這個方法的核心。
那麼咱們須要讓元素大小發生改變時,使得 scrollLeft 或者 scrollTop 發生改變,從而觸發 scroll 事件,進一步得知其大小發生了改變。

visibility: hidden; opacity: 0; position: absolute;讓本身變得虛無

addEventListener("scroll", scrollListener, true) 在捕捉階段攔截事件,使用false無效

div.expand-trigger 變大

div.expand-trigger 變小

animationstart來監聽顯示,好比style.display = 'none'而後style.display = 'block'

問題:

  1. 額外建立四個元素節點以及一個style節點
  2. 事件都掛載了元素自己身上,

ResizeObserver

原生自帶的方案, 兼容性並不高, resize-observer-polyfill 基於resize和MutationOberver的polyfill實現了ResizeObserver。

const resizeObserver = new ResizeObserver(entries => {
        for (let entry of entries) {
            
            console.log(entry.target.id, `height:${entry.contentRect.height}  width:${entry.contentRect.width}`);
        }
        });
        resizeObserver.observe(document.querySelector('#my_element'));
        resizeObserver.observe(document.querySelector('#my_element2'));

此外

固然,我以爲還

  1. 定時器 + getComputedStyle 也是很低成本的實現。
  2. resize + MutationOberver 也是很簡單的方案。
相關文章
相關標籤/搜索