Vue+Element页面生成快照截图

页面部分:

html 复制代码
<template>
  <div ref="homePage" class="home-container rel">
    <div class="snap-box abs">
      <div title="页面快照" class="z-pointer" @click="newSnapShot()">
        <img :src="snapCamera" alt="快照生成">
      </div>
    </div>
    <el-image-viewer
      v-if="imgUrl"
      :on-close="()=>{imgUrl=''}"
      :url-list="[imgUrl]" />
  </div>
</template>

js代码部分:

javascript 复制代码
/**
 * 图片blob转图片base64
 * @param blob
 */
export const blobToBase64 = (blob) => {
	return new Promise((resolve, reject) => {
		const fileReader = new FileReader();
		fileReader.onload = (e) => {
			resolve(e.target.result);
		};
		// readAsDataURL
		fileReader.readAsDataURL(blob);
		fileReader.onerror = () => {
			reject(new Error('blobToBase64 error'));
		};
	});
}



import html2canvas from 'html2canvas';
import { blobToBase64 } from '@/utils/helper.js';


export default {
  name: 'Home',
  components: {
    'el-image-viewer': () => import('element-ui/packages/image/src/image-viewer'),
  },
  data() {
    return {
      tooltipRemark,
      loading: false,
      imgUrl: '',
    };
  },
  methods: {
    // 生成快照
    newSnapShot() {
      this.loading = true;
      const { ClipboardItem } = window;
      html2canvas(this.$refs.homePage).then((canvas) => {
        // 将canvas转为blob对象
        canvas.toBlob(async (blob) => {
          if (typeof (navigator.clipboard) === 'undefined' && !ClipboardItem) {
            await blobToBase64(blob).then((res) => {
              this.imgUrl = res;
              this.$message({
                message: '快照生成成功',
                type: 'success',
                duration: 2000,
              });
            }).catch(() => {
              this.$message({
                message: '快照生成失败',
                type: 'warning',
                duration: 2000,
              });
            }).finally(() => {
              this.loading = false;
            });
            return;
          }
          // 将blob对象放入剪切板item中
          // eslint-disable-next-line no-undef
          const data = [new ClipboardItem({ [blob.type]: blob })];
          // 写入剪切板,成功会执行resolve,失败则走reject
          await navigator.clipboard.write(data).then(() => {
            this.$message({
              message: '已保存到粘贴板',
              type: 'success',
              duration: 2000,
            });
            this.loading = false;
          }, () => {
            this.$message({
              message: '保存截图失败',
              type: 'warning',
              duration: 2000,
            });
            this.loading = false;
          });
        }, 'image/png');
      }).catch(() => {
        this.loading = false;
      });
    },
  },
};
相关推荐
程序哥聊面试4 分钟前
React + TS 初始化新项目报错解决方法
前端·react.js·npm
codeGoogle6 分钟前
2026 年 IM 怎么选?聊聊 4 家主流即时通讯方案的差异
android·前端·后端
_OP_CHEN7 分钟前
【前端开发之JavaScript】(二)JS基础语法上篇:吃透变量 / 类型 / 输入输出
开发语言·javascript·html·ecmascript·前端开发·网页开发
C澒12 分钟前
从单体到分布式:SLDS 2.0 全球物流履约网络架构演进之路
前端·分布式·架构·系统架构·教育电商·交通物流
We་ct15 分钟前
LeetCode 21. 合并两个有序链表:两种经典解法详解
前端·算法·leetcode·链表·typescript
70asunflower17 分钟前
TypeScript / JavaScript / Node.js:现代工程化语言体系全景解析
javascript·typescript·node.js
2501_9419820518 分钟前
Python开发:外部群消息自动回复
java·前端·数据库
予你@。19 分钟前
uni-app(Vue3)实现自定义 Tab 切换滑块效果(微信小程序)
vue.js·微信小程序·uni-app
墨染青竹梦悠然23 分钟前
基于Django+vue的单词学习平台
前端·vue.js·后端·python·django·毕业设计·毕设
mCell25 分钟前
从一个想法到可发布:我把博客接进 MCP 的完整实践
前端·node.js·mcp