vue组件vue-esign实现电子签名


Posted in Vue.js onApril 21, 2022

vue vue-esign签字板demo

使用vue-esign让用户能够在手动签字并返回为base64或者file格式的文件流

安装

npm install vue-esign --save

在main.js中全局引用

import vueEsign from 'vue-esign'
Vue.use(vueEsign)

Demo 

<template>
  <div class="esigns">
    <vue-esign
      ref="esign"
      style="
        width: 100%;
        height: 400px
      "
      :isCrop="isCrop"
      :lineWidth="lineWidth"
      :lineColor="lineColor"
      :bgColor.sync="bgColor"
    />
    <div class="btn">
      <van-button type="primary" @click="handleReset">重置</van-button>
      <van-button type="info" @click="handleGenerate">确定</van-button>
    </div>
  </div>
</template>
<script>
export default {
  name: "Esign",
  data() {
    return {
      lineWidth: 6,
      lineColor: "#000000",
      bgColor: "",
      resultImg: "",
      isCrop: false,
    };
  },
  methods: {
    handleReset() {
      // 清除
      this.$refs.esign.reset();
    },
    handleGenerate() {
      // 获取base64
      var _this = this;
      _this.$refs.esign
        .generate()
        .then((res) => {
          // 转成文件
          var file = _this.dataURLtoFile(res);
            console.log("file:",file )
          //调用接口
          uploadFile(file).then(({ data }) => {
           console.log("data:",data)
          });
        })
        .catch((err) => {
          _this.$toast(err); 
        });
    },
    // 将base64转换为file
    dataURLtoFile(dataurl) {
      let arr = dataurl.split(",");
      let mime = arr[0].match(/:(.*?);/)[1];
      let bytes = atob(arr[1]); // 解码base64
      let n = bytes.length;
      let ia = new Uint8Array(n);
      while (n--) {
        ia[n] = bytes.charCodeAt(n);
      }
      return new File([ia], "easign.jpg", { type: mime });
    },
  },
};
</script>
<style scoped>
.btn {
  display: flex;
  justify-content: space-around;
  margin-top: 10px;
}
</style>

vue移动端电子签名demo

HTML

<template>
    <div id='canvasBox'>
        <div ref="canvasBox">
             <canvas id="canvas" ref="canvas" height="150"></canvas>
        </div>
        <div class="row row-space-between">
          <button  @click="onClickCancle">取消</button>
          <button @click="clear">重签</button>
          <button @click="save">确认</button>
        </div>
        <!-- <img :src="singImgUrl" alt /> -->
    </div>
</template>

JS相关代码

<script>
var draw;
var preHandler = function(e) {
  e.preventDefault();
};
class Draw {
  constructor(el) {
    this.el = el;
    this.canvas = document.getElementById(this.el);
    this.cxt = this.canvas.getContext("2d");
    this.stage_info = canvas.getBoundingClientRect();
    this.path = {
      beginX: 0,
      beginY: 0,
      endX: 0,
      endY: 0
    };
  }
  init(btn) {
    var that = this;
    this.canvas.addEventListener("touchstart", function(event) {
      document.addEventListener("touchstart", preHandler, false);
      that.drawBegin(event);
    });
    this.canvas.addEventListener("touchend", function(event) {
      document.addEventListener("touchend", preHandler, false);
      that.drawEnd();
    });
    this.clear(btn);
  }
  drawBegin(e) {
    var that = this;
    window.getSelection()
      ? window.getSelection().removeAllRanges()
      : document.selection.empty();
    this.cxt.strokeStyle = "#BC4C2D";
    this.cxt.beginPath();
    this.cxt.moveTo(
      e.changedTouches[0].clientX - this.stage_info.left,
      e.changedTouches[0].clientY - this.stage_info.top
    );
    this.path.beginX = e.changedTouches[0].clientX - this.stage_info.left;
    this.path.beginY = e.changedTouches[0].clientY - this.stage_info.top;
    canvas.addEventListener("touchmove", function() {
      that.drawing(event);
    });
  }
  drawing(e) {
    this.cxt.lineTo(
      e.changedTouches[0].clientX - this.stage_info.left,
      e.changedTouches[0].clientY - this.stage_info.top
    );
    this.path.endX = e.changedTouches[0].clientX - this.stage_info.left;
    this.path.endY = e.changedTouches[0].clientY - this.stage_info.top;
    this.cxt.stroke();
  }
  drawEnd() {
    document.removeEventListener("touchstart", preHandler, false);
    document.removeEventListener("touchend", preHandler, false);
    document.removeEventListener("touchmove", preHandler, false);
    //canvas.ontouchmove = canvas.ontouchend = null
  }
  clear(btn) {
    this.base64Id = "";
    this.cxt.clearRect(0, 0, 500, 600);
  }
  save() {
    var blank = document.createElement("canvas"); //系统获取一个空canvas对象
    blank.width = canvas.width;
    blank.height = canvas.height;
    let flag = canvas.toDataURL("image/png") == blank.toDataURL(); //比较值相等则为空;
    if (flag) {
      return "0";
    } else {
      return canvas.toDataURL("image/png");
    }
  }
}
export default {
  data() {
    return {
      singImgUrl: ""
    };
  },
  methods: {
	 clear() {
        draw.clear();
        this.base64Id = "";
	 },
   	save() {
      var data = "";
      data = draw.save();
      if (data == "0") {
      		this.$toast("请先签名再点击确定哦~");
      } else {
	      this.singImgUrl = data;
	      ///data 就是得到的base64格式的签名图片,根据业务这里可上传到服务器
      }
      // 
    },
},
 mounted() {
 document.getElementById("canvasBox").addEventListener("touchmove", (e) => {
      e.preventDefault();
    });//阻止浏览器默认行为,防止签名浏览器下拉-------很重要
    this.base64Id = "";
    let _width = this.$refs.canvasBox.offsetWidth;
    this.$refs.canvas.width = _width; //适配移动端宽度给canvas
    draw = new Draw("canvas");
    draw.init();
  }
}
</script>

CSS 自行美化,相信大家都没得问题。


Tags in this post...

Vue.js 相关文章推荐
Vue Elenent实现表格相同数据列合并
Nov 30 Vue.js
解决Vue-cli3没有vue.config.js文件夹及配置vue项目域名的问题
Dec 04 Vue.js
vue使用exif获取图片旋转,压缩的示例代码
Dec 11 Vue.js
VUE中鼠标滚轮使div左右滚动的方法详解
Dec 14 Vue.js
Vue解决移动端弹窗滚动穿透问题
Dec 15 Vue.js
Vue项目打包部署到apache服务器的方法步骤
Feb 01 Vue.js
VUE实现吸底按钮
Mar 04 Vue.js
vue3.0 项目搭建和使用流程
Mar 04 Vue.js
Vue图片裁剪组件实例代码
Jul 02 Vue.js
简单聊聊Vue中的计算属性和属性侦听
Oct 05 Vue.js
VUE中的v-if与v-show区别介绍
Mar 13 Vue.js
vue打包时去掉所有的console.log
Apr 10 Vue.js
vue动态绑定style样式
Apr 20 #Vue.js
Vue OpenLayer测距功能的实现
vue 给数组添加新对象并赋值
Apr 20 #Vue.js
vue 数字翻牌器动态加载数据
Apr 20 #Vue.js
vue3.0 数字翻牌组件的使用方法详解
Apr 20 #Vue.js
vue封装数字翻牌器
Apr 20 #Vue.js
vue特效之翻牌动画
Apr 20 #Vue.js
You might like
PHP - Html Transfer Code
2006/10/09 PHP
获取php页面执行时间,数据库读写次数,函数调用次数等(THINKphp)
2013/06/03 PHP
php无限级分类实现方法分析
2016/10/19 PHP
Webkit的跨域安全问题说明
2011/09/13 Javascript
深入理解JavaScript系列(8) S.O.L.I.D五大原则之里氏替换原则LSP
2012/01/15 Javascript
动态加载dtree.js树treeview(示例代码)
2013/12/17 Javascript
在jquery中combobox多选的不兼容问题总结
2013/12/24 Javascript
IE6兼容透明背景图片及解决方案
2015/08/19 Javascript
AngularJS入门教程之 XMLHttpRequest实例讲解
2016/07/27 Javascript
AngularJs bootstrap详解及示例代码
2016/09/01 Javascript
使用JSON作为函数的参数的优缺点
2016/10/27 Javascript
requirejs按需加载angularjs文件实例
2017/06/08 Javascript
代码详解JS操作剪贴板
2018/02/11 Javascript
jQuery中图片展示插件highslide.js的简单dom
2018/04/22 jQuery
Bootstrap Table中的多选框删除功能
2018/07/15 Javascript
Vue如何提升首屏加载速度实例解析
2020/06/25 Javascript
JavaScript实现串行请求的示例代码
2020/09/14 Javascript
JS实现炫酷轮播图
2020/11/15 Javascript
原生js实现表格循环滚动
2020/11/24 Javascript
[01:58]DOTA2上海特级锦标赛现场采访:RTZ这个ID到底好不好
2016/03/25 DOTA
[00:13]天涯墨客二技能展示
2018/08/25 DOTA
python利用elaphe制作二维条形码实现代码
2012/05/25 Python
python下os模块强大的重命名方法renames详解
2017/03/07 Python
python 实现在一张图中绘制一个小的子图方法
2019/07/07 Python
python 实现线程之间的通信示例
2020/02/14 Python
在Mac中配置Python虚拟环境过程解析
2020/06/22 Python
CSS3关于z-index不生效问题的解决
2020/02/19 HTML / CSS
沙龙级头发造型工具:FOXYBAE
2018/07/01 全球购物
New Balance俄罗斯官方网上商店:购买运动鞋
2020/03/02 全球购物
全球异乡人的跨境社交电商平台:Kouhigh口嗨网
2020/07/24 全球购物
应届生的求职推荐信范文
2013/11/30 职场文书
晨会主持词
2014/03/17 职场文书
导游词之寿县报恩寺
2020/01/19 职场文书
mysql配置SSL证书登录的实现
2021/09/04 MySQL
Python基础 括号()[]{}的详解
2021/11/07 Python
JavaScript异步操作中串行和并行
2021/11/20 Javascript