發生問題場景
系統頁面使用tabs
標簽頁,當有多個組件,有使用eCharts圖表的頁面時,其中的一個頁面或其他頁面使用了F11
的頁面全屏
,關閉
全屏后圖表
會收縮
起來(注:
固定eCharts的width、height 的參數值是無影響,按照固定參數大小展示),如使用百分比:
<div ref={myChartRef} style={{ width: '100%', height: '100%' }} />
會收縮,這時候window.addEventListener(‘resize’)(僅監聽窗口)
無法監聽
優缺點
在監聽窗口或元素尺寸變化時,window.addEventListener(‘resize’) 和 ResizeObserver 是兩種常見方法,各有優缺點。以下是詳細對比:
1. window.addEventListener(‘resize’)
優點
廣泛兼容性
- 所有瀏覽器均支持,包括
舊版本
(如 IE9+)。 - 簡單直接
- 監聽整個窗口的尺寸變化,代碼簡潔,適合全局布局調整。
- 性能優化空間
- 可通過防抖(debounce)或節流(throttle)減少回調觸發頻率。
缺點
- 僅監聽窗口
無法直接監聽
特定元素的尺寸變化(如 div、iframe 等)。- 觸發
頻率
高 - 瀏覽器窗口調整時可能連續觸發
多次
回調,需手動優化
(如防抖)。 - 無法獲取變化前后的尺寸
- 需自行存儲上一次的尺寸值進行比較。
- 移動端問題
- 虛擬鍵盤彈出/收起可能觸發 resize,但實際窗口尺寸未變,需額外處理。
示例代碼
javascript
window.addEventListener('resize', debounce(() => {console.log('窗口尺寸變化:', window.innerWidth, window.innerHeight);
}, 200));function debounce(fn, delay) {let timer;return () => {clearTimeout(timer);timer = setTimeout(fn, delay);};
}
2. ResizeObserver
優點
- 監聽任意元素
- 可
精確監聽
特定DOM
元素的尺寸變化(包括 width、height、padding、border 等)。 - 高效觸發
瀏覽器內部優化
,僅在尺寸實際變化時觸發回調,避免
冗余計算。- 提供詳細信息
- 回調中直接返回元素的 contentRect(內容尺寸)和 borderBoxSize(邊框盒尺寸)。
- 現代標準
- 專為動態尺寸監聽設計,是
W3C
推薦方案。
缺點
兼容性限制
不支持 IE 和舊版 Edge
(需 Polyfill 或降級處理)。- 初始尺寸不觸發
僅在尺寸變化時觸發
,若需初始尺寸需額外調用一次。- 循環觀察風險
- 若回調中修改元素尺寸,可能導致無限循環(需謹慎處理)。
示例代碼
const element = document.getElementById('target');
const observer = new ResizeObserver((entries) => {for (let entry of entries) {console.log('元素尺寸變化:', entry.contentRect);}
});observer.observe(element); // 開始觀察
// observer.unobserve(element); // 停止觀察
對比總結
// 優先使用 ResizeObserver,不支持時回退到 resize + 防抖
if ('ResizeObserver' in window) {const observer = new ResizeObserver(/* ... */);observer.observe(element);
} else {// 使用 resize 事件 + 防抖(需通過其他方式獲取元素尺寸)
}
根據項目需求和瀏覽器支持情況靈活選擇即可。