主项目通过iframe嵌套子项目,子项目弹框无法全屏

之所以调研iframe技术,是因为一个问题引起的。

问题:主项目通过iframe嵌套子项目,子项目弹框无法全屏,请问有什么方案解决呢?

经过调研,有以下方式解决:

  1. 主项目实现一个弹框,子项目和主项目进行通信,对弹框进行控制。
  2. 子项目通过getContainer把弹框挂载到主项目的body上。
  3. 如果是简单的弹框,可以手写一个。

第1种方案是比较通用的方案,比较简单。

但有时候会存在这样的问题,主项目无法修改,怎么办?只能用第3种方案,自己手写一个弹框了。

好多人会使用第2中方案,因为毕竟a-modal给出了这样的api,但第2种方案有坑,并且坑不小。它不是一个通用方案不建议使用,实在没办法,也可以尝试着一用。

第2种方案会存在以下问题:

  • 子项目挂载到主项目的body上,a-modal的样式丢失。

以上问题如何解决:

第一种方法:在主项目上放一个a-modal,用v-show="false"隐藏,这样子项目挂载到主项目body上的a-modal也有了样式。

主项目

xml 复制代码
<template>
  <a-card title="主项目 - 子项目展示">
    <div>
      <iframe
        ref="iframeRef"
        :src="subAppUrl"
        frameborder="0"
      ></iframe>
    </div>
    <!-- 可以用v-show -->
    <a-modal v-show="false" v-model:open="open" title="Basic Modal" @ok="handleOk">
      <p>Some contents...</p>
      <p>Some contents...</p>
      <p>Some contents...</p>
    </a-modal>
  </a-card>
</template>

<script setup>
import { ref } from 'vue'

const iframeRef = ref(null)
// 通过代理访问子项目,确保同域名
const subAppUrl = ref('/sub-app/')


const open = ref(true);

const showModal = () => {
  open.value = true;
};

const handleOk = (e) => {
  console.log(e);
  open.value = false;
};
</script>
ini 复制代码
<script setup>
import { ref } from 'vue'

const iframeRef = ref(null)
// 通过代理访问子项目,确保同域名
const subAppUrl = ref('/sub-app/')


const open = ref(true);

const showModal = () => {
  open.value = true;
};

const handleOk = (e) => {
  console.log(e);
  open.value = false;
};
</script>

子项目

ini 复制代码
<a-modal
  v-model:open="modalVisible"
  title="弹框"
  width="600px"
  :get-container="getContainer"
  @ok="handleOk"
  @cancel="handleCancel"
>
  <div class="modal-content">
    <h2>这是一个弹框</h2>
    <p>弹框内容区域</p>
    <a-space>
      <a-button>按钮1</a-button>
      <a-button>按钮2</a-button>
    </a-space>
  </div>
</a-modal>
javascript 复制代码
// 获取主项目的body作为弹框容器
const getContainer = () => {  
  try {
    // 通过 window.parent 访问主项目的 document
    if (window.parent && window.parent !== window.self) {
      console.log('window.parent.document:', window.parent.document)
      if (window.parent.document && window.parent.document.body) {
        console.log('成功获取父窗口body')
        return window.parent.document.body
      }
    } else {
      console.warn('window.parent 不存在或等于 window.self')
    }
  } catch (e) {
    // 如果跨域,会抛出错误,则使用当前窗口的body
    console.error('无法访问父窗口,使用当前窗口body:', e)
  }
  console.log('使用当前窗口body')
  return document.body
}

第二种方式:需要把a-modal的样式注入进去。

这种代码就不贴了,个人觉得比较麻烦,并且还有不确定的边界,个人不建议用这种方式。

相关推荐
我爱加班、、3 分钟前
Websocket能携带token过去后端吗
前端·后端·websocket
AAA阿giao3 分钟前
从零拆解一个 React + TypeScript 的 TodoList:模块化、数据流与工程实践
前端·react.js·ui·typescript·前端框架
杨超越luckly9 分钟前
HTML应用指南:利用GET请求获取中国500强企业名单,揭秘企业增长、分化与转型的新常态
前端·数据库·html·可视化·中国500强
hedley(●'◡'●)39 分钟前
基于cesium和vue的大疆司空模仿程序
前端·javascript·vue.js·python·typescript·无人机
qq5_81151751541 分钟前
web城乡居民基本医疗信息管理系统信息管理系统源码-SpringBoot后端+Vue前端+MySQL【可直接运行】
前端·vue.js·spring boot
百思可瑞教育41 分钟前
构建自己的Vue UI组件库:从设计到发布
前端·javascript·vue.js·ui·百思可瑞教育·北京百思教育
百锦再41 分钟前
Vue高阶知识:利用 defineModel 特性开发搜索组件组合
前端·vue.js·学习·flutter·typescript·前端框架
CappuccinoRose1 小时前
JavaScript 学习文档(二)
前端·javascript·学习·数据类型·运算符·箭头函数·变量声明
这儿有一堆花1 小时前
Vue 是什么:一套为「真实业务」而生的前端框架
前端·vue.js·前端框架
全栈前端老曹1 小时前
【MongoDB】深入研究副本集与高可用性——Replica Set 架构、故障转移、读写分离
前端·javascript·数据库·mongodb·架构·nosql·副本集