vue 移动端实现手写签名效果,功能很完美,保存时保存为base64格式。
base64转file文件格式 vue中将base64转file文件格式
刚好项目用到此功能,就网上找了一下,清理了无用代码,简单方便,因为项目中多个地方需要使用,所以我将它整理为组件,通过ref和传值控制,下面代码我单独整理出来,可自行封装组件(只支持移动端,不支持pc端)。
代码中,css自行修改一下宽高,背景之类即可。
代码如下
-
<template>
-
<!-- 手写签名组件 -->
-
<div class="page sign-page">
-
<div class="content">
-
<div class="sign-wrap" id="signWrap">
-
<canvas id="myCanvas" width="100%" height="100%">
</canvas>
-
</div>
-
</div>
-
<div class="con-btn">
-
<span class="staging-btn size14" @click="clearArea()">清除签名
</span>
-
<span class="submit-btn size14" @click="saveSign()">确认签名
</span>
-
</div>
-
</div>
-
</template>
-
<script>
-
export
default {
-
name:
"signature",
-
data() {
-
return {
-
image:
"",
-
mousePressed:
false,
-
c:
"",
-
ctx:
"",
-
lastX:
0,
-
lastY:
0,
-
};
-
},
-
mounted() {
-
this.image =
"";
-
this.mousePressed =
false;
-
var lastX, lastY;
-
this.ctx =
document.getElementById(
"myCanvas").getContext(
"2d");
-
this.c =
document.getElementById(
"myCanvas");
-
var signWrap =
document.getElementById(
"signWrap");
-
this.c.width = signWrap.clientWidth;
// 设置宽度
-
this.c.height = signWrap.clientHeight;
// 设置高度
-
// 监听touchstart事件,touchmove事件,touchend事件等事件
-
this.InitThis();
-
},
-
methods: {
-
InitThis() {
-
// 触摸屏
-
var that =
this;
-
this.c.addEventListener(
-
"touchstart",
-
function (event) {
-
if (event.targetTouches.length ==
1) {
-
event.preventDefault();
// 阻止浏览器默认事件,重要
-
var touch = event.targetTouches[
0];
-
this.mousePressed =
true;
-
that.Draw(
-
touch.pageX -
this.offsetLeft,
-
touch.pageY -
this.offsetTop,
-
false
-
);
-
}
-
},
-
false
-
);
-
this.c.addEventListener(
-
"touchmove",
-
function (event) {
-
if (event.targetTouches.length ==
1) {
-
event.preventDefault();
// 阻止浏览器默认事件,重要
-
var touch = event.targetTouches[
0];
-
if (
this.mousePressed) {
-
that.Draw(
-
touch.pageX -
this.offsetLeft,
-
touch.pageY -
this.offsetTop,
-
true
-
);
-
}
-
}
-
},
-
false
-
);
-
this.c.addEventListener(
-
"touchend",
-
function (event) {
-
if (event.targetTouches.length ==
1) {
-
event.preventDefault();
// 阻止浏览器默认事件,防止手写的时候拖动屏幕,重要
-
this.mousePressed =
false;
-
}
-
},
-
false
-
);
-
// 鼠标
-
this.c.onmousedown =
function (event) {
-
this.mousePressed =
true;
-
that.Draw(
-
event.pageX -
this.offsetLeft,
-
event.pageY -
this.offsetTop,
-
false
-
);
-
};
-
this.c.onmousemove =
function (event) {
-
if (
this.mousePressed) {
-
that.Draw(
-
event.pageX -
this.offsetLeft,
-
event.pageY -
this.offsetTop,
-
true
-
);
-
}
-
};
-
this.c.onmouseup =
function (event) {
-
this.mousePressed =
false;
-
};
-
},
-
Draw(x, y, isDown) {
-
if (isDown) {
-
this.ctx.beginPath();
-
this.ctx.strokeStyle =
"#000";
// 颜色
-
this.ctx.lineWidth =
3;
// 线宽
-
this.ctx.lineJoin =
"round";
-
this.ctx.lineMax =
10;
// 设置画笔最大线宽
-
this.ctx.lineMin =
3;
// 设置画笔最小线宽
-
this.ctx.linePressure =
1.2;
// 设置画笔笔触压力
-
this.ctx.smoothness =
30;
// 设置画笔笔触大小变化的平滑度
-
this.ctx.moveTo(
this.lastX,
this.lastY);
-
this.ctx.lineTo(x, y);
-
this.ctx.closePath();
-
this.ctx.stroke();
-
}
-
this.lastX = x;
-
this.lastY = y;
-
},
-
// 清空画板
-
clearArea() {
-
this.ctx.setTransform(
1,
0,
0,
1,
0,
0);
-
this.ctx.clearRect(
0,
0,
this.ctx.canvas.width,
this.ctx.canvas.height);
-
},
-
// 提交签名
-
saveSign() {
-
this.checkEmpty();
// 调用 表单非空验证
-
},
-
checkEmpty() {
-
var c =
document.getElementById(
"myCanvas");
// 获取html的canvas对象,我这个id="myCanvas"
-
if (
this.isCanvasBlank(c)) {
-
alert(
"请在签名区域签名后再次确认");
-
return;
-
}
else {
-
var image =
this.c.toDataURL(
"image/png");
// 得到生成后的签名base64位 url 地址
-
console.log(image);
// 打印图片base64 url
-
}
-
},
-
// 验证canvas画布是否为空函数
-
isCanvasBlank(canvas) {
-
var blank =
document.createElement(
"canvas");
// 系统获取一个空canvas对象
-
blank.width = canvas.width;
-
blank.height = canvas.height;
-
return canvas.toDataURL() == blank.toDataURL();
// 比较值相等则为空
-
},
-
},
-
};
-
</script>
-
<
style
lang="
scss"
scoped>
-
.page {
-
width:
100%;
-
.content {
-
width:
100%;
-
height:
1.7rem;
-
background:
url(../assets/img/photo_qmq.png) no-repeat;
-
background-size:
100%
100%;
-
background-position: center center;
-
.sign-wrap {
-
width:
100%;
-
height:
100%;
-
}
-
}
-
.con-btn {
-
width:
100%;
-
display: flex;
-
align-content: center;
-
justify-content: space-between;
-
opacity:
0.75;
-
span {
-
font-size:
0.14rem;
-
width:
100%;
-
height:
0.48rem;
-
display: flex;
-
align-items: center;
-
justify-content: center;
-
}
-
.staging-btn {
-
color:
#4154ff;
-
background:
#fff;
-
}
-
.submit-btn {
-
color:
#fff;
-
background:
#4154ff;
-
}
-
}
-
}
-
-
</
style>
原文围观地址 http://www.sharedblog.cn/post/217.html
转载:https://blog.csdn.net/tianpeng1996/article/details/113704211
查看评论