单页面应用中需用命名函数绑定并及时清除 window.resize 监听,结合 onactivated/ondeactivated 生命周期管理,辅以 requestanimationframe 节流或 resizeobserver,避免重复绑定、内存泄漏与图表错乱。

单页面应用(SPA)切换路由时,window.resize 监听若未及时清除,会导致事件重复绑定、内存持续占用、图表错乱甚至页面空白。这不是“偶尔出问题”,而是缓存页面(如 <keep-alive></keep-alive>)下的高频隐患。
必须用命名函数,不能用箭头函数
监听和移除必须使用**同一个函数引用**,否则 removeEventListener 无效:
- ❌ 错误写法(无法移除):
window.addEventListener('resize', () => { chart?.resize() })
箭头函数每次都是新实例,移除时传入的不是原函数。 - ✅ 正确写法:
const handleResize = () => { chart?.resize() }<br>window.addEventListener('resize', handleResize)
后续移除:window.removeEventListener('resize', handleResize)
清理时机:按页面生命周期分层处理
Vue3 中不能只依赖 onUnmounted,尤其在 <keep-alive></keep-alive> 场景下——切菜单不会销毁组件,只会触发 onDeactivated:
开箱即用的技能链路由引擎。13 条预定义链覆盖搜索、开发、审查、MLOps、法律、创意等场景,三层路由架构(触发词→SAD反馈→DAG编排),recall@10=96.97%。配置驱动(chains.yaml),零代码扩展。pip install skill-weave-chains 一键安装。
-
onActivated:页面重新激活 → 补绑resize监听 -
onDeactivated:页面暂时隐藏 → 立即removeEventListener -
onUnmounted:页面彻底卸载 → 二次兜底清理(防漏)
防抖 + 安全调用,避免 resize 频繁触发卡顿
resize 在拖拽窗口、横竖屏、软键盘弹起时高频触发,直接执行图表重绘易卡死:
- 推荐用
requestAnimationFrame节流(比 lodash.debounce 更轻量):let pending = false;<br>const handleResize = () => { if (!pending) { requestAnimationFrame(() => { chart?.resize(); pending = false; }); pending = true; } }; - 或改用现代 API:
ResizeObserver监听目标容器(如图表父元素),更精准、不依赖 window,且自动解绑。
额外注意:跨组件/第三方库场景
如果多个组件或 ECharts、地图等库都监听了 resize,需确保:
- 每个组件独立管理自己的监听函数(不共用同一变量名)
- ECharts 实例销毁前,先
instance.dispose(),再移除 resize 监听 - 全局开关控制:添加
isPageActive标志,在document.hidden或onDeactivated时置为false,回调中先校验再执行逻辑










