vue通过iframe引入一个外链地址,怎么保证每次切换回这个已经打开的tab页的时候iframe不会重新加载

我有很多的报表页。这些页面是通过外链引入的。他们只有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>
相关推荐
瑞瑞小同学1 小时前
处理echarts x轴内容过多,重叠问题
前端·javascript·echarts
HexCIer1 小时前
面向未来的原子化 CSS:UnoCSS 核心架构分析与 Tailwind CSS 现状
前端·css·vite
程序员黑豆2 小时前
鸿蒙应用开发中的单位详解:px、vp、fp、lpx
前端·harmonyos
像我这样帅的人丶你还2 小时前
MCP + npm:给五年前的老系统接上AI
前端·javascript·agent
南一Nanyi2 小时前
依赖注入和控制反转
前端·设计模式·nestjs
小村儿2 小时前
连载14-实战篇--一个半月,我一个人和 Claude Code 搭出一套数字人工程
前端·后端·ai编程
愚公移码2 小时前
蓝凌EKP18产品:流程虚拟机(PVM)
java·开发语言·前端
promiseThen3 小时前
5 分钟上手 Markdown:标题到表格、代码块与简历实战
前端
web66liang3 小时前
webpack4+vue2项目使用 sass-embedded 导致的 DockerfIle 构建失败的问题
前端
Larcher3 小时前
LangChain RAG 排错实录:.env 为什么没有生效
vue.js·后端