设置电子签名

在这里插入图片描述

设置点赞签名代码

export class Signature {width: number = 300height: number = 300canvas!: HTMLCanvasElementctx!: CanvasRenderingContext2Dprivate drawing: boolean = falsepreTask: string[] = []nextTask: string[] = []private allTask: { x: number; y: number; color: string }[][] = []private itemTask: { x: number; y: number; color: string }[] = []private lineWidth: number = 1private color: string = '#000'private background: string = '#ff234234'constructor(canvas: HTMLCanvasElement,width: number,height: number,lineWidth?: number,color?: string) {if (canvas instanceof HTMLCanvasElement != true) {console.warn('请传入一个Canvas元素')return}this.canvas = canvasthis.canvas.width = width || this.widththis.canvas.height = height || this.heightthis.lineWidth = lineWidth || this.lineWidththis.color = color || this.colorthis.ctx = canvas.getContext('2d') as CanvasRenderingContext2Dthis.eventListener()this.initCanvas()this.setColor()this.setLineWidth()}private initCanvas() {this.allTask = []this.preTask = []this.nextTask = []this.ctx.imageSmoothingEnabled = truethis.ctx.lineJoin = 'round' // 圆角连接this.ctx.lineCap = 'round' // 圆角线帽// this.ctx.translate(0.5, 0.5)this.ctx.strokeStyle = this.color}private eventListener() {this.canvas.addEventListener('mousedown', this.canvasMouseDown.bind(this))this.canvas.addEventListener('mousemove', this.canvasMouseMove.bind(this))this.canvas.addEventListener('mouseup', this.canvasMouseEnd.bind(this))this.canvas.addEventListener('mouseout', this.canvasMouseEnd.bind(this))}removeEventListener() {this.canvas.removeEventListener('mousedown',this.canvasMouseDown.bind(this))this.canvas.removeEventListener('mousemove',this.canvasMouseMove.bind(this))this.canvas.removeEventListener('mouseup', this.canvasMouseEnd.bind(this))this.canvas.removeEventListener('mouseout', this.canvasMouseEnd.bind(this))}private canvasMouseDown(e: MouseEvent) {this.drawing = truethis.ctx.beginPath() // 开始绘制this.ctx.moveTo(e.offsetX, e.offsetY) // 移动到this.itemTask.push({x: e.offsetX,y: e.offsetY,color: this.color,})}private canvasMouseMove(e: MouseEvent) {if (this.drawing) {this.ctx.lineTo(e.offsetX, e.offsetY) // 绘制到this.ctx.stroke() // 绘制this.itemTask.push({x: e.offsetX,y: e.offsetY,color: this.color,})}}private canvasMouseEnd(e: MouseEvent) {this.drawing = falsethis.ctx.closePath()const index = this.preTask.findIndex((item) => {return item === this.toDataURL()})if (index === -1) {this.preTask.push(this.toDataURL())}this.allTask.push(this.itemTask)this.itemTask = []}/*** @description: 设置画笔颜色* @param {string} color* @return {*}*/setColor(color?: string) {this.color = color || this.colorthis.ctx.strokeStyle = this.color}/*** @description: 设置画布背景* @param {string} background* @return {*}*/setBgColor(background?: string) {this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height)this.background = background || this.backgroundthis.ctx.fillStyle = this.backgroundthis.ctx.fillRect(0, 0, this.canvas.width, this.canvas.height)this.allTask.length ? this.setPathLine() : ''}/*** @description: 设置折线* @return {*}*/private setPathLine() {const taskFilter = this.allTask.filter((item) => {return item.length})taskFilter.forEach((item) => {this.ctx.beginPath()this.ctx.moveTo(item[0].x, item[0].y)item.forEach((list, index) => {if (index) {this.ctx.lineTo(list.x, list.y)this.ctx.strokeStyle = list.colorthis.ctx.stroke()}})this.ctx.closePath()})}/*** @description: 设置线条宽度* @param {number} width* @return {*}*/setLineWidth(width?: number) {this.lineWidth = width || this.lineWidththis.ctx.lineWidth = this.lineWidth}/*** @description: 清空画布* @return {*}*/clear() {this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height)this.preTask = []this.nextTask = []this.allTask = []}/*** @description: 上一个画布* @return {*}*/setPreImage() {if (this.preTask.length > 0) {const currentData = this.preTask.pop()!this.allTask.pop()!this.nextTask.push(currentData)const previousData = this.preTask[this.preTask.length - 1]if (previousData) {this.drawImage(previousData).then(() => console.log('撤销成功'))} else {this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height)console.log('画布已清空')}console.log(`撤销: preTask = ${this.preTask.length}, nextTask = ${this.nextTask.length}`)}}/*** @description: 下一个画布* @return {*}*/setNextImage() {if (this.nextTask.length > 0) {const nextData = this.nextTask.pop()!this.preTask.push(nextData)this.drawImage(nextData).then(() => console.log('恢复成功'))console.log(`恢复: preTask = ${this.preTask.length}, nextTask = ${this.nextTask.length}`)}}/*** @description: 导入图片* @param {string} src* @return {*}*/drawImage(src: string,x = 0,y = 0,width = this.canvas.width,height = this.canvas.height) {return new Promise((resolve, reject) => {const image = new Image()image.onload = (e) => {this.ctx.clearRect(x, y, width, height)this.ctx.drawImage(image, x, y, width, height)resolve(e)}image.onerror = (e) => {reject(e)}image.src = src})}/*** @description: 转换成base64* @return {*}*/toDataURL(format: 'image/png' | 'image/jpeg' = 'image/png',quality: number = 1.0): string {return this.canvas.toDataURL(format, quality)}/*** @description: 导出图片* @return {*}*/exportToImage(fileName: string) {const url = this.canvas.toDataURL('image/png')var link = document.createElement('a')link.download = fileNamelink.href = urllink.click()}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1524068.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

Leetcode - 周赛413

目录 一,3274. 检查棋盘方格颜色是否相同 二,3275. 第 K 近障碍物查询 三,3276. 选择矩阵中单元格的最大得分 四,3277. 查询子数组最大异或值 一,3274. 检查棋盘方格颜色是否相同 本题就是找规律,假设白…

EPLAN中如何将图纸导出为PDF文件并设置页边距?

EPLAN中如何将图纸导出为PDF文件并设置页边距? 如下图所示,在项目中选中需要导出的图纸页, 如下图所示,点击上方页-----导出------PDF, 如下图所示,在弹出的窗口中设置导出文件的名称、输出目录、输出颜色,这里建议勾选“使用打印边距”, 如下图所示,继续点击下方的设…

论文速读|重新审视奖励设计与评估:用于强健人型机器人站立与行走控制的方法

论文地址:https://arxiv.org/pdf/2404.19173 这篇论文为类人机器人站立和行走(SaW)控制器的持续可衡量改进奠定了基础。通过引入一套定量实际基准测试方法,作者展示了现有控制器的优缺点,并通过基准测试指导新控制器的…

论文速读|自然语言的最优控制合成:机遇与挑战

项目地址:Optimal Control Synthesis from Natural Language: Opportunities and Challenges 介绍了一种从自然语言自动生成最优控制器的框架,该框架主要包括以下几个步骤:首先,通过人类用户提供的初始文本和系统描述,…

源代码如何防泄露?做好这十条轻松应对

源代码防泄露是一个多方面的安全问题,涉及到技术、管理和物理等多个层面。以下是一些有效的策略和方法,结合深信达的SDC防泄密软件,来实现源代码的防泄露: 1. **访问控制**:实施基于角色的访问控制(RBAC&am…

JUC-无锁之CAS

问题提出 (应用之互斥) package cn.itcast; import java.util.ArrayList; import java.util.List; interface Account {// 获取余额Integer getBalance();// 取款void withdraw(Integer amount);/*** 方法内会启动 1000 个线程,每个线程做 -10 元 的操作* 如果初始…

深度学习系列73:使用rapidStructure进行版面分析

1. 概述 项目地址https://github.com/RapidAI/RapidStructure?tabreadme-ov-file 2. 文档方向分类示例 安装$ pip install rapid-orientation import cv2 from rapid_orientation import RapidOrientation orientation_engine RapidOrientation() img cv2.imread(test_im…

C++笔记---string类(简单地使用)

1. string类介绍 string类是C标准库中给出的一种类类型,其目的是为了代替C语言中的字符串。 C语言中,字符串是以\0结尾的一些字符的集合,为了操作方便,C标准库中提供了一些str系列的库函数,但是这些库函数与字符串是…

【时时三省】(C语言基础)指针进阶 例题

山不在高,有仙则名。水不在深,有龙则灵。 ----CSDN 时时三省 字符数组例题: arr后面放了六个字符 所以这个数组的元素个数就是6 第一个arr 因为他计算的是一整个数组的大小 就是打印6 第二个arr0 arr没有单独放在它的内部 所以它计算的就是…

深智城基于超融合数据库MatrixOne的一站式交通大数据平台改造

在智慧交通应用中,数据处理需求极为复杂,涉及人、车辆、道路和环境等多个方面,产生了大量异构数据。交通管理人员需要对这些数据进行实时分析和决策,以应对各种交通事件。然而,在实际生产中会发现数据处理缺陷、管理复…

智慧平台赋能政务管理,声通科技助力政务管理智能化

在智能时代的大潮中,政务管理也在不断寻求创新与突破,在这方面,涌现出了很多优秀的公司。比如声通科技的子公司西安金讯数智信息技术有限公司,就在AI政务热线领域有很多创新成果,为政务管理的智能化升级提供了新思路。…

windows安装php7.4

windows安装php7.4 1.通过官网下载所需的php版本 首先从PHP官网(https://www.php.net/downloads.php)或者Windows下的PHP官网(http://windows.php.net/download/)下载Windows版本的PHP安装包。下载后解压到一个路径下。 2.配…

爆改YOLOv8|利用yolov10的PSA注意力机制改进yolov8-高效涨点

1,本文介绍 PSA是一种改进的自注意力机制,旨在提升模型的效率和准确性。传统的自注意力机制需要计算所有位置对之间的注意力,这会导致计算复杂度高和训练时间长。PSA通过引入极化因子来减少需要计算的注意力对的数量,从而降低计算…

视频汇聚平台LntonAIServer视频质量诊断功能--偏色检测与噪声检测

随着视频监控技术的不断进步,视频质量成为了决定监控系统性能的关键因素之一。LntonAIServer新增的视频质量诊断功能,特别是偏色检测和噪声检测,进一步强化了视频监控系统的可靠性和实用性。下面我们将详细介绍这两项功能的技术细节、应用场景…

window系统开机执行bat脚本

1,win R 打开运行对话框,然后如下图所示输入 第二,打开启动文件夹后,将想要执行的bat脚本,创建快捷方式,放在这里,重启电脑时就会执行这个程序

【Canvas与纹饰】环形小蜜蜂纹饰

【成图】 【代码】 <!DOCTYPE html> <html lang"utf-8"> <meta http-equiv"Content-Type" content"text/html; charsetutf-8"/> <head><title>环形小蜜蜂纹饰</title><style type"text/css"&g…

《OpenCV计算机视觉》—— 模板匹配

文章目录 一、模板匹配简单介绍二、三个主要函数的介绍1.执行模板匹配函数-cv2.matchTemplate()2.查找最佳匹配函数-cv2.minMaxLoc()3.在原图上绘制匹配区域函数-cv2.rectangle() 三、代码实现 一、模板匹配简单介绍 在Python中&#xff0c;模板匹配是一种在图像中查找与给定模…

【Next】4. 全局通用布局快速搭建

笔记来源&#xff1a;编程导航 基础布局 Next.js 支持全局根布局&#xff08;每个页面都会生效&#xff09;以及嵌套布局&#xff08;可以只对部分页面生效&#xff09;&#xff0c;详情可 参考文档。 在 src 下新建 layouts 目录&#xff0c;用于存放项目中的各种布局。在该目…

无法访问Github?Steam++来帮你

前言 有许多小伙伴发现在国内访问Github真的真的很难&#xff0c;毕竟Github的DNS很容易就被***。 昨天还看到有小伙伴在群上聊天问&#xff1a;如何访问Github&#xff0c;实际上你只需要安装个加速器&#xff0c;或者使用国内的镜像站就可以轻松访问。 当然&#xff0c;如…

【面试八股总结】MySQL 锁:全局锁、表级锁、行级锁

1. 全局锁 顾名思义&#xff0c;全局锁就是对整个数据库实例加锁。 MySQL 提供了⼀个加全局读锁的方法&#xff1a; flush tables with read lock 释放全局锁&#xff0c;执行命令&#xff1a; unlock tables 需要让整个库处于只读状态的时候&#xff0c;可以使用全局锁命…