网页复制保持原始样式

Flchy 于 2019-10-01 发布

事情起源于今天对微信公众号排版时遇到的一个问题

平时都是使用新榜编辑器对公众号内容进行排版,但是想要的布局上面没有,于是就想到参考编辑器的做法,自己把布局用网页写好然后复制粘贴到公众号的编辑器不就行了么

尝试

先做一个简单的 flex 左右布局试了一下,然后复制粘贴到公众号的编辑器,发现图片的格式是乱掉的

00

于是尝试拿到剪切板复制的内容,看看到底存放的是什么

document.addEventListener('paste', function(ev) {
  console.log(ev.clipboardData.getData('text/html'))
})

最终得到如下内容。可以发现浏览器会默认为你加上许多样式,而且图片的百分比宽度会变成固定像素宽度

01

于是我把网页的源码复制到了新榜编辑器的源码编辑模式里,再进行复制粘贴到公众号查看,发现格式竟然没变化!这里拿到它的剪切板内容看了下,发现内容就是网页的原始格式

02

解决问题

到这里问题就很明显了,如果能修改剪切板的内容就行了,在复制时把内容替换为 outerHTML,然后阻止默认事件不让浏览器在添加额外的样式就行了

// 点击按钮触发拷贝
function copy() {
  window.copyDOM = document.querySelector('#s1')
  document.execCommand('copy')
}
// 监听拷贝事件
// Ctrl+c,document.execCommand('copy')均会触发
document.addEventListener('copy', function(ev) {
  if (window.copyDOM) {
    let domHtml = window.copyDOM.outerHTML
    // 拿到数据后清除,不影响默认的copy
    window.copyDOM = null
    // 这里必须是text/html
    ev.clipboardData.setData('text/html', domHtml)
    // 阻止默认复制事件
    ev.preventDefault()
  }
})

至此完美实现了自己的需求,如果以后需要在微信公众号做一些复杂布局时,完全可以通过上面的方式自己实现

参考

MDN web docs

Chrome 浏览器读写系统剪切板

复制粘贴的高级玩法