我有很多的报表页。这些页面是通过外链引入的。他们只有id是不一样的。
我的页面是这样写的。router定义成
{ path: '/report-template/:id', title: '统计模版', name: 'report-template', component: () => import(/*webpackChunkName: "report-template"*/ '@/views/report-management/report-template.vue'), },
report-template.vue
<template> <div class="external-page-container"> <iframe :src="srcUrl" frameborder="0" width="100%" allowfullscreen ></iframe> </div> </template> <script> export default { name:'report-template', data() { return { id: 0, srcUrl: "", } }, watch: { '$route.params' (to) { // 路由发生变化.iframe地址改变 this.$nextTick(()=>{ this.getIframe() }) }, }, mounted(){ this.getIframe() }, methods:{ getIframe(){ this.id=this.$route.params.id; this.srcUrl=`https://jm/jmreport/view/${this.id}`; //拼接访问地址 } } } </script> <style scoped> .external-page-container{ width: 100%; height: 100%; position: relative; } iframe{ position: absolute; top: 0; bottom: 0; height: 100%; } </style>
上面能实现点击不同的报表菜单。展示不同的报表数据。
但是发现按照上面的写法打开了一个报表菜单之后再点击别的。再次切换回这个报表的菜单。页面会刷新一下,重新加载这个iframe。如何做到打开之后就记住当时的状态,包含输入框查询的内容。
这时候我们可以把iframe打开过的id都保存起来,把所有的iframe都以v-show的形式显示和隐藏。并且注意最外层的要加上keep-alive。下面cachePage包含所有打开的路由页面
<!-- 路由渲染的右侧所有数据的地方在这 包含着缓存数据 -->
<keep-alive :include="cachePage">
<router-view></router-view>
</keep-alive>
然后优化这个report-template.vue
<template> <div class="external-page-container"> <div v-for="openedId in openedReportIds" :key="openedId" class="iframe-wrapper" v-show="currentId == openedId" > <!-- 使用缓存的 urlMap,打开后的url再次切换回去可以记住之前的筛选内容 --> <iframe :src="urlMap[openedId]" frameborder="0" width="100%" height="100%" allowfullscreen ></iframe> </div> </div> </template> <script> export default { name: 'report-template', data() { return { currentId: null, openedReportIds: [], urlMap: {} // 缓存每个 ID 对应的完整 URL } }, watch: { '$route.params.id': { handler(newId) { if (newId && newId !== this.currentId) { this.currentId = newId; if (!this.openedReportIds.includes(newId)) { this.openedReportIds.push(newId); // 只在首次打开时计算并缓存 URL this.urlMap[newId] = this.getIframeUrl(newId); } } }, immediate: true } }, methods: { getIframeUrl(id) { this.id=this.$route.params.id; this.srcUrl=`https://jm/jmreport/view/${this.id}`; //拼接访问地址 } } } </script> <style scoped> .external-page-container{ width: 100%; height: 100%; position: relative; } iframe{ position: absolute; top: 0; bottom: 0; height: 100%; } </style>