Files
tms-erp-web/.workbuddy/memory/2026-09-18.md
T
gxwebsoft b4e12a671f fix(views): 修复独立页切换时弹窗残留问题
- 独立整页固定使用普通 div 容器,取消动态切换 el-dialog 避免切换时弹窗 DOM 残留
- 删除相关 dialogVisible、dialogTitle、页脚弹窗动态分支代码以简化逻辑
- watch $route 调整,优化独立页初始化流程,避免不必要的关闭弹窗操作
- 新增 closeInnerDialogs 方法,页面卸载或 keep-alive deactivate 时关闭所有二级弹窗
- 对 loading-manage 与 project-apply 两个模块同步改造,统一处理弹窗状态和容器渲染
- 解决 keep-alive 缓存导致旧弹窗一直挂载在 body 上的问题,改善用户切换体验
2026-09-18 10:17:48 +08:00

3.0 KiB
Raw Blame History

2026-09-18

修复:改成独立整页后点左侧菜单仍弹出旧弹窗(loading-manage / project-apply

现象:配载单管理、项目管理已改为「新增/编辑/详情走独立整页」,但从独立页返回或直接点左侧菜单时,页面上仍会盖出一个老的 el-dialog(新增项目管理 / 配载单)。

根因(已读 Vue runtime-core 源码确认):

  • src/router/tab.jstabKey(默认 fullPath)为每个标签建一个具名 wrapper 组件放进 wrapperMapsrc/page/index/layout.vue<keep-alive :include="$store.getters.tagsKeep"> 缓存 —— 每个标签页一个实例,全部缓存不销毁。
  • 组件被 deactivate 后仍会随 $route(全局响应式)重新渲染;此时 isStandalonePage 变 false<component :is="isStandalonePage ? 'div' : 'el-dialog'"> 由 div 翻回 el-dialog,而 v-modelprojectBox/dialogVisible)仍是 trueappend-to-body 使弹窗 Teleport 到 body。
  • KeepAlive.deactivatemove(vnode, storageContainer, ..., moveType=OUT),但 TeleportImpl.movemoveTeleport)忽略传入的 moveType、一律按 REORDER 处理 → teleport 出去的 DOM 不会被搬回 storage container,永久残留在 document.body 上并显示出来。

修法(不回退 tab.js 的 return wrapper 提交 c1c4fa1,改修根因):

  • 独立页容器固定为 <div v-if="isXxxPage">,不再按路由回退成 el-dialog
  • 页内其它 append-to-body 二级弹窗加 deactivated() / beforeUnmount()closeInnerDialogs() 把 v-model 置 false。

改动文件

  • src/views/business/loading-manage.vue:容器改 <div v-if="isStandalonePage">;删 dialogVisibledialogTitleresetLoadingDialogclearLoadingDialog、页脚弹窗分支(含「清空」);watch.$route 简化;新增 closeInnerDialogs()routeChange / commonAddress / candidateSearch+ deactivated/beforeUnmount
  • src/views/business/project-apply.vue:容器改 <div v-if="isProjectFormPage">;删 projectFormContainer/projectFormContainerPropsprojectBoxresetProjectDialoghandleCancelProjectcloseProjectForm 简化为直接 push 列表;新增 closeInnerDialogs()changeRecordDetail / 附件文档预览 / 图片预览 / 选人)+ deactivated/beforeUnmount

校验dev server(2889) curl 两个 .vue 及其 scoped style 模块,均 HTTP 200500 才是编译失败)。vite build 因沙箱敏感内容保护会在 facelogin.vue 中断,未用。

遗留同类风险(未改,已告知用户)business/components/waybill-manage-page.vuedetailContainer 在 PageDetail / el-dialog 间切)、settlement/components/{pre,formal}-settlement-editor.vuetransport-reconciliation-editor.vuepageMode ? 'div':'el-dialog')、business/components/waybill-import-dialog.vuestandalone/createPage)。统一修法:容器类型在 created() 锁定,不随路由/prop 翻转。

未提交:上述改动 + 上一轮 loading-manage 独立页改造均未 commit。