前言:
由于window.postMessage是单向的,导致开发中通讯就变得异常麻烦;以下封装了postMessage的收发函数,并且支持了回调。
一、方案的思考
每一次发送消息,都可以定义一个发送消息id、回调id;通过id标识来处理该轮消息的收发。
二、定义消息标识
const sendTag = '-sendContent' // 发送的标识
const receiveTag = '-receiveContent' // 接收回调的标识
// 生成唯一ID
const guid = () => {
return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
const r = Math.random() * 16 | 0
const v = c === 'x' ? r : (r & 0x3 | 0x8)
return v.toString(16)
})
}
三、监听方函数
/**
* 监听postMessage消息
*/
const receiveMessage = (event) => {
const { msgUuid = '' } = event.data
if (!msgUuid.includes(sendTag)) return // 仅接收sendTag标识的消息
const result = {
msgUuid: msgUuid.replace(sendTag, receiveTag),
content: '回调消息'
}
window.postMessage(result, '*')
}
window.addEventListener('message', receiveMessage, false)
四、发送消息函数
/**
* postMessage,支持回调
* @param {Object} request 发送的内容
*
*/
export const syncSendMessage = (request = {}) => {
const id = guid() // 生成消息id
const msgUuid = id + sendTag // 发送的消息Id
const receiveId = id + receiveTag // 接收回调的消息Id
return new Promise(resolve => {
const receiveMessage = (event) => {
if (event.data?.msgUuid === receiveId) {
delete event.data.msgUuid
window.removeEventListener('message', receiveMessage, false)
resolve(event.data)
}
}
window.addEventListener('message', receiveMessage, false)
window.postMessage({ ...request, msgUuid }, '*')
})
}
发送例子:
const res = await syncSendMessage({
content: '发送的消息'
})
console.log('收到的结果', res) // { content: '回调消息' }
有用的话麻烦关注收藏一下🌹🌹🌹~
同时欢迎私信交流