专栏首页热爱IT前端爬坑日记之vue内嵌iframe并跨域通信

前端爬坑日记之vue内嵌iframe并跨域通信

由于该项目是基于原本的安卓app,做的微信h5,所以原来的使用webview的页面现在需要在vue中实现,那就是使用iframe 查看了很多很多文档,其中这一篇是很有价值的 https://gist.github.com/pboji...点击预览

下面将3天的爬坑最终以问答的方式总结如下:

1、Vue组件中如何引入iframe?

2、vue如何获取iframe对象以及iframe内的window对象?

3、vue如何向iframe内传送信息?

4、iframe内如何向外部vue发送信息?

1、Vue组件中如何引入iframe?

<template>
  <div class="act-form">
    <iframe :src="src"></iframe>
  </div>
</template>

<script>

export default {
  data () {
    return {
      src: '你的src'
    }
  }
}
</script>
如上,直接通过添加iframe标签,src属性绑定data中的src,第一步引入就完成了

2、vue如何获取iframe对象以及iframe内的window对象?

在vue中,dom操作比不上jquery的$('#id')来的方便,但是也有办法,就是通过ref
<template>
  <div class="act-form">
    <iframe :src="src" ref="iframe"></iframe>
  </div>
</template>

<script>

export default {
  data () {
    return {
      src: '你的src'
    }
  },
  mounted () {
    // 这里就拿到了iframe的对象
    console.log(this.$refs.iframe)
  }
}
</script>

然后就是获取iframe的window对象,因为只有拿到这个对象才能向iframe中传东西

<template>
  <div class="act-form">
    <iframe :src="src" ref="iframe"></iframe>
  </div>
</template>

<script>

export default {
  data () {
    return {
      src: '你的src'
    }
  },
  mounted () {
    // 这里就拿到了iframe的对象
    console.log(this.$refs.iframe)
    // 这里就拿到了iframe的window对象
    console.log(this.$refs.iframe.contentWindow)
  }
}
</script>

3、vue如何向iframe内传送信息?

通过postMessage,具体关于postMessage是什么,自己去google,

我的理解postMessage是有点类似于UDP协议,就像短信,是异步的,你发信息过去,但是没有返回值的,只能内部处理完成以后再通过postMessage向外部发送一个消息,外部监听message

为了让postMessage像TCP,为了体验像同步的和实现多通信互不干扰,特别制定的message结构如下
{
  cmd: '命令',
  params: {
    '键1': '值1',
    '键2': '值2'
  }
}

通过cmd来区别这条message的目的

具体代码如下

<template>
  <div class="act-form">
    <iframe :src="src" ref="iframe"></iframe>
    <div @click="sendMessage">向iframe发送信息</div>
  </div>
</template>

<script>

export default {
  data () {
    return {
      src: '你的src',
      iframeWin: {}
    }
  },
  methods: {
    sendMessage () {
      // 外部vue向iframe内部传数据
      this.iframeWin.postMessage({
        cmd: 'getFormJson',
        params: {}
      }, '*')
    },
  },
  mounted () {
    // 在外部vue的window上添加postMessage的监听,并且绑定处理函数handleMessage
    window.addEventListener('message', this.handleMessage)
    this.iframeWin = this.$refs.iframe.contentWindow
  },
  handleMessage (event) {
    // 根据上面制定的结构来解析iframe内部发回来的数据
    const data = event.data
    switch (data.cmd) {
      case 'returnFormJson':
        // 业务逻辑
        break
      case 'returnHeight':
        // 业务逻辑
        break
    }
  }
}
</script>

4、iframe内如何向外部vue发送信息?

现在通过点击“向iframe发送信息”这个按钮,从外部vue中已经向iframe中发送了一条信息

{
  cmd: 'getFormJson',
  params: {}
}

那么iframe内部如何处理这个信息呢?

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title>iframe Window</title>
    <style>
        body {
            background-color: #D53C2F;
            color: white;
        }
    </style>
</head>
<body>

    <h1>Hello there, i'm an iframe</h1>

    <script>
        // 向父vue页面发送信息
        window.parent.postMessage({
            cmd: 'returnHeight',
            params: {
              success: true,
              data: document.body.scrollHeight + 'px'
            }
        }, '*');

        // 接受父页面发来的信息
        window.addEventListener("message", function(event){
          var data = event.data;
          switch (data.cmd) {
            case 'getFormJson':
                // 处理业务逻辑
                break;
            }
        });
    </script>
</body>
</html>

至此内部的收发信息已经解决了,外部的收发也已经解决了,快去解决你的问题吧

在这里先直接给出我项目的源码

<template>
  <div class="act-form">
    <div class="nav">
      <img src="https://cxkccdn.oss-cn-shanghai.aliyuncs.com/lesai_img/icon_back_white.png" @click="back()">
      <div class="title">报名</div>
    </div>
    <div class="iframe-out">
      <iframe :src="src" ref="iframe" @load="iframeLoad"></iframe>
    </div>
    <div v-if="isLoaded" class="send-form"><div class="send" @click="sendMessage()">提交</div></div>
  </div>
</template>

<!-- Add "scoped" attribute to limit CSS to this component only -->
<style lang="sass" rel="stylesheet/sass">
  @import "style.scss";
</style>

<script>
import { Toast, Indicator } from 'mint-ui'
import api from '@/utils/api'

export default {
  data () {
    return {

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • 查询数据

    双面人
  • python生成pdf报告、python实现html转换为pdf报告[python3] 原

    系统安装wkhtmltopdf:参考 https://github.com/JazzCore/python-pdfkit/wiki/Installing-wkh...

    双面人
  • HBase Filter及对应Shell 转

    比较运算符 CompareFilter.CompareOp 比较运算符用于定义比较关系,可以有以下几类值供选择:

    双面人
  • 深入理解iframe

    iframe 用于在页面内显示页面,使用 <iframe> 会创建包含另外一个文档的内联框架(即行内框架)

    Leophen
  • 根据获取内部元素的高度,设置iframe的高度

    德顺
  • iframe 解析

    简介:iframe在日常的开发中经常用到,本随笔在参考http://blog.csdn.net/cuew1987/article/details/1126515...

    郑小超.
  • Selenium自动化测试-8.iframe处理

    在上一篇:Selenium自动化测试-获取元素属性信息,介绍了如何获取元素的内容、属性、状态信息。写自动化脚本有时会遇到 iframe嵌套页面,这时直接定位是不...

    橙子探索测试
  • Selenium自动化测试-8.iframe处理

    在上一篇:Selenium自动化测试-获取元素属性信息,介绍了如何获取元素的内容、属性、状态信息。写自动化脚本有时会遇到 iframe嵌套页面,这时直接定位是不...

    ITester软件测试小栈
  • BUG赏金 | 当我发现iFrame注入时的利用

    iFrame注入是一种非常常见的跨站脚本攻击。它包括已插入到网页或文章内容的一个或多个iframe代码,或一般下载一个可执行程序或进行其他动作使网站访客的电脑妥...

    PaperPen
  • 如何通过iframe调用其他页面的内容

      我们在建站的时候经常会在页面出现同样的内容,比如公司简介之类的,这些东西很长,会减低网页的原创程度,相似度太高,对SE不是很友好。这时我们可以考虑把这部分内...

    ytkah

扫码关注云+社区

领取腾讯云代金券