Vue implements one-click screenshot function

1. Install HTML Canvas

npm install html2canvas --save

2. Introduce in the required Vue components

import html2canvas from "html2canvas";

3. Define the click button and screenshot method

/*定义的截图菜单*/
<el-button
      class="button-upload"
      size="mini"
      title="生成图片"
      type="success"
      @click="toImage()"
      icon="el-icon-upload el-icon--right">上传截图</el-button>


/*js内容*/
const imageTofile = ref(null)
const toImage = () => {
  //如果步骤信息为空,那么就不需要上传截图文件
  //此处可以根据自己需求做是否满足截图上传的判断前置条件
  if (props.steps.length === 0) {
    ElMessage.warning({
      message: '还没有添加步骤详情,无需上传截图信息',
    })
    return
  }

  // 手动创建一个 canvas 标签
  const canvas = document.createElement('canvas')
  // 获取父标签,意思是这个标签内的 DOM 元素生成图片
  // imageTofile是给截图范围内的父级元素自定义的ref名称
  let canvasBox = imageTofile.value
  // 获取父级的宽高
  const width = parseInt(window.getComputedStyle(canvasBox).width)
  const height = parseInt(window.getComputedStyle(canvasBox).height)
  // 宽高 * 2 并放大 2 倍 是为了防止图片模糊
  canvas.width = width * 2
  canvas.height = height * 2
  canvas.style.width = width + 'px'
  canvas.style.height = height + 'px'
  const context = canvas.getContext('2d')
  context.scale(2, 2)
  html2canvas(canvasBox, { allowTaint: true }).then((canvas) => {
    //document.body.appendChild(canvas)  页面布局会乱
    //转换base64
    debugger
    const capture = canvas.toDataURL('image/png')
    //下载浏览器弹出下载信息的属性
    const saveInfo = {
      //导出文件格式自己定义,我这里用的是时间作为文件名
      download: getNowTime() + `.png`,
      href: capture,
    }
    //下载,浏览器弹出下载文件提示
    downloadFile(saveInfo)

    //调用服务端保存接口
    axios
      .post('/controller/testCases/uploadStempImg', {
        caseId: props.steps[0].caseId,
        projectId: props.steps[0].projectId,
        base64Img: capture,
      })
      .then((resp) => {
        if (resp['code'] === 2000) {
          ElMessage.success({
            message: resp['message'],
          })
          emit('flush')
        }
      })
  })
}

/*获取当前时间,为截图的图片提供名称 */
const getNowTime = () => {
  const yy = new Date().getFullYear()
  const MM =
    new Date().getMonth() + 1 < 10
      ? '0' + (new Date().getMonth() + 1)
      : new Date().getMonth() + 1
  const dd =
    new Date().getDate() < 10
      ? '0' + new Date().getDate()
      : new Date().getDate()
  const HH =
    new Date().getHours() < 10
      ? '0' + new Date().getHours()
      : new Date().getHours()
  const mm =
    new Date().getMinutes() < 10
      ? '0' + new Date().getMinutes()
      : new Date().getMinutes()
  const ss =
    new Date().getSeconds() < 10
      ? '0' + new Date().getSeconds()
      : new Date().getSeconds()
  return yy + MM + dd + '-' + HH + mm + ss
}

//下载截图
const downloadFile = (saveInfo) => {
  const element = document.createElement('a')
  element.style.display = 'none'
  for (const key in saveInfo) {
    element.setAttribute(key, saveInfo[key])
  }
  document.body.appendChild(element)
  element.click()
  setTimeout(() => {
    document.body.removeChild(element)
  }, 300)
}

4. Don't forget to add the ref attribute to the parent within the scope of the screenshot, so that the screenshot can capture a specific part according to the business

  <div ref="imageTofile"></div>

Reference: Vue realizes web page screenshot_suoh's Blog's blog-CSDN blog_vue screenshot

Guess you like

Origin blog.csdn.net/PhilipJ0303/article/details/126766363