微信小程序canvas实现人员签名
这里使用获取canvas节点实现的小程序最新的api
签字面板效果图
wxml部分:
<view class="container" >
<view class="sig_txt">
<canvas type="2d" id="myCanvas"
style="width:{{width}}px;height:{{height}}px;"
bindtouchstart="handleTouchStart1"
bindtouchmove="handleTouchMove1"
bindtouchcancel="handleTouchEnd1"
bindtouchend="handleTouchEnd1"
></canvas>
</view>
<view class="sig_st_justify sig_wh">
<view class="sig_st_justify sig_left_imgwh1" bindtap="handldrewrite">
<view style="margin-left: 3px;"><image class="sig_cimg" src="/images/svg/r_refresh.svg" mode="aspectFit" /></view>
<view>撤销</view>
</view>
<view class="sig_st_justify sig_left_imgwh2" bindtap="confirmWrite">
<view style="margin-left: 3px;"><image class="sig_cimg" src="/images/svg/s_pen.svg" mode="aspectFit" /></view>
<view>确定</view>
</view>
</view>
</view>
js部分:
Page({
data: {
startX: undefined, // 线条的坐标点
startY: undefined,
canvas: '',
ctx: '',
pr:0,
width: 296,
height: 300,
stindex:0,
imgsingurl:"",
},
// 点击返回上级页面
goBack: function() {
let pages = getCurrentPages(); //获取小程序页面栈
let beforePage = pages[pages.length - 2]; //获取上个页面的实例对象
//传参给上个页面
beforePage.setData({
signimgurl: this.data.imgsingurl //当前编写签名传参给父页面
});
wx.navigateBack({ //返回上一页
delta: 1
})
},
// 获取系统信息
getSystemInfo() {
let that = this;
wx.getSystemInfo({
success(res) {
that.setData({
pr:res.pixelRatio,
width: res.windowWidth-24,
// height: res.windowHeight - 75,
})
}
})
},
// 初始化画布
initCanvas() {
const pr = this.data.pr; // 像素比
const query = wx.createSelectorQuery();
query.select('#myCanvas').fields({ node: true, size: true }).exec((res) => {
const canvas = res[0].node;
const ctx = canvas.getContext('2d');
canvas.width = this.data.width*pr; // 画布宽度
canvas.height = this.data.height*pr; // 画布高度
ctx.scale(pr,pr); // 缩放比
ctx.lineGap = 'round';
ctx.lineJoin = 'round';
ctx.lineWidth = 3; // 字体粗细
ctx.font = '40px Arial'; // 字体大小,
ctx.fillStyle = '#ecf0ef'; // 填充颜色
ctx.fillText('请在此区域签名', res[0].width / 2 - 140, res[0].height / 2)
this.setData({
ctx: ctx,
canvas: canvas
})
})
},
//开始
handleTouchStart1(e) {
if (this.data.stindex==0) {
//清空(请在此区域签名)提示信息
this.data.ctx.clearRect(0, 0, this.data.width, this.data.height);
this.data.ctx.beginPath();
}
this.setData({
startX: e.touches[0].x,
startY: e.touches[0].y,
stindex: 1,
})
},
// 移动
handleTouchMove1(e) {
this.data.ctx.moveTo(this.data.startX, this.data.startY);
this.data.ctx.lineTo(e.touches[0].x, e.touches[0].y);
this.data.ctx.stroke();
this.setData({
startX: e.touches[0].x,
startY: e.touches[0].y,
})
},
// 结束
handleTouchEnd1() {
this.data.ctx.closePath();
},
// 清空画布
handldrewrite:function () {
this.data.ctx.clearRect(0, 0, this.data.width, this.data.height);
this.data.ctx.beginPath();
this.data.ctx.fillText('请在此区域签名', this.data.width / 2 - 140, this.data.height / 2);
this.setData({
startX: "",
startY: "",
stindex:0,
})
},
// 确认提交
confirmWrite() {
var that=this;
if (!this.data.startX && !this.data.startY) {
wx.showModal({
title: '提示',
content: '签名内容不能为空!',
showCancel: false
});
return false;
};
wx.canvasToTempFilePath({
canvas: this.data.canvas,
success(res) {
const tempFilePath = res.tempFilePath; // 取图片文件路径
//将 tempFilePath 传递给后端接口
wx.uploadFile({
url: 'https://xxxxx',//后端接口
filePath:tempFilePath,
name: 'file',
success (res){
if (res.data) {
var dedata= decodeURIComponent(res.data);
var datalist= JSON.parse(dedata);
if (datalist.data) {
that.setData({
imgsingurl: datalist.data,
})
that.goBack();
}
}
},
fail: function(res) {
wx.showModal({
title: '提示',
content: '上传签名错误!',
showCancel: false
});
}
})
}
})
},
onLoad: function (options) {
this.getSystemInfo();
this.initCanvas();
}
})
wxss部分:
.sig_st_justify{
display: flex;
justify-content: flex-start;
align-items: center;
}
.sig_wh{
width: 100%;
}
.sig_txt{
color: #1A1A1A;
font-size: 14px;
margin-left: 10px;
margin-bottom: 10px;
border: 1px solid #E4E4E4;
}
.sig_cimg{
width: 26px;
height: 26px;
margin-top: 8px;
}
.sig_left_imgwh1{
width: 75px;
height: 30px;
line-height: 30px;
color: #FF3939;
font-size: 18px;
border: 1px solid #cccccc;
border-radius: 10px;
margin-left: calc((50% - 75px)/2);
}
.sig_left_imgwh2{
width: 75px;
height: 30px;
line-height: 30px;
color: #4C74F4 ;
font-size: 18px;
border: 1px solid #4C74F4;
border-radius: 10px;
margin-left: calc((50% - 75px)/2);
}