中文亚洲精品无码_熟女乱子伦免费_人人超碰人人爱国产_亚洲熟妇女综合网

當(dāng)前位置: 首頁(yè) > news >正文

WordPress自定義計(jì)算小紅書seo排名

WordPress自定義計(jì)算,小紅書seo排名,做網(wǎng)站能收回嗎,裝修設(shè)計(jì)費(fèi)多少錢一平方一、先看效果 小程序canvas電子簽名 二、文檔 微信小程序canvas 組件文檔 微信小程序canvas API文檔 H5Canvas文檔 三、分析 1、初始話Canvas容器 2、Canvas觸摸事件,bindtouchstart(手指觸摸動(dòng)作開(kāi)始)、bindtouchmove(手指觸摸…

一、先看效果

小程序canvas電子簽名

二、文檔

微信小程序canvas 組件文檔
微信小程序canvas API文檔
H5Canvas文檔

三、分析

1、初始話Canvas容器
2、Canvas觸摸事件,bindtouchstart(手指觸摸動(dòng)作開(kāi)始)、bindtouchmove(手指觸摸后移動(dòng))、bindtouchend(手指觸摸動(dòng)作結(jié)束)、bindtouchcancel(手指觸摸動(dòng)作被打斷,如來(lái)電提醒,彈窗)
3、記錄每次從開(kāi)始到結(jié)束的路徑段
4、清除、撤銷

四、代碼分析

1、頁(yè)面的布局、Canvas容器的初始化

1、先將屏幕橫過(guò)來(lái),index.json配置文件,“pageOrientation”: “l(fā)andscape”
2、wx.getSystemInfoSync() 獲取可使用窗口的寬高,賦值給Canvas畫布(注意若存在按鈕區(qū)域、屏幕安全區(qū)之類的,需要減去)

 // 獲取可使用窗口的寬高,賦值給Canvas(寬高要減去上下左右padding的20,以及高度要減去footer區(qū)域)wx.createSelectorQuery().select('.footer') // canvas獲取節(jié)點(diǎn).fields({node: true, size: true}) // 獲取節(jié)點(diǎn)的相關(guān)信息,node:是否返回節(jié)點(diǎn)對(duì)應(yīng)的 Node 實(shí)例,size:是否返回節(jié)點(diǎn)尺寸.exec((res) => {// 獲取手機(jī)左側(cè)安全區(qū)域(劉海)const deviceInFo = wx.getSystemInfoSync()const canvasWidth = deviceInFo.windowWidth - 20 - deviceInFo?.safeArea?.left || 0const canvasHeight = deviceInFo.windowHeight - res[0].height - 20console.log('canvasWidth', canvasWidth);console.log('canvasHeight', canvasHeight);this.setData({deviceInFo,canvasWidth,canvasHeight})this.initCanvas('init')})

3、通過(guò)wx.createSelectorQuery()獲取到canvas節(jié)點(diǎn),隨即可獲取到canvas的上下文實(shí)例

  // 初始話Canvas畫布initCanvas() {let ctx = nulllet canvas = null// 獲取Canvas畫布以及渲染上下文wx.createSelectorQuery().select('#myCanvas') // canvas獲取節(jié)點(diǎn).fields({node: true, size: true}) // 獲取節(jié)點(diǎn)的相關(guān)信息,node:是否返回節(jié)點(diǎn)對(duì)應(yīng)的 Node 實(shí)例,size:是否返回節(jié)點(diǎn)尺寸.exec((res) => { // 執(zhí)行所有的請(qǐng)求。請(qǐng)求結(jié)果按請(qǐng)求次序構(gòu)成數(shù)組// Canvas 對(duì)象實(shí)例canvas = res[0].node// Canvas 對(duì)象上下文實(shí)例(動(dòng)畫動(dòng)作繪圖等都是在他的身上完成)ctx = canvas.getContext('2d')// Canvas 畫布的實(shí)際繪制寬高const width = res[0].width;const height = res[0].height;// 獲取設(shè)備像素比const dpr = wx.getWindowInfo().pixelRatio;// 初始化畫布大小canvas.width = width * dpr;canvas.height = height * dpr;// 畫筆的顏色ctx.fillStyle = 'rgb(200, 0, 0)';// 指定了畫筆(繪制線條)操作的線條寬度ctx.lineWidth = 5// 縮小/放大圖像ctx.scale(dpr, dpr)this.setData({canvas, ctx});})},
2、線條的繪制

通過(guò)canva組件的觸摸事件bindtouchstart、bindtouchmove、bindtouchend、bindtouchcancel結(jié)合canvas的路徑繪制的方法moveTo(x,y)、lineTo(x,y)、stroke()來(lái)實(shí)現(xiàn)一段線條的繪制

1、bindtouchstart手指觸摸動(dòng)作開(kāi)始,結(jié)合moveTo(x,y) 用來(lái)設(shè)置繪圖起始坐標(biāo)的方法確定線段的開(kāi)始坐標(biāo)

  // 手指觸摸動(dòng)作開(kāi)始bindtouchstart(event) {let {type, changedTouches} = event;let {x, y} = changedTouches[0];ctx.moveTo(x, y); // 設(shè)置繪圖起始坐標(biāo)。},

2、bindtouchend手指觸摸動(dòng)作結(jié)束,結(jié)合lineTo(x,y) 來(lái)繪制一條直線,最后stroke()渲染路徑

  // 手指觸摸動(dòng)作結(jié)束bindtouchend(event) {let {type, changedTouches} = event;let {x, y} = changedTouches[0];ctx.lineTo(x, y);// 繪制ctx.stroke();},

3、但這只是一條直線段,并未實(shí)現(xiàn)簽名所需的曲線(曲線實(shí)質(zhì)上也是由無(wú)數(shù)個(gè)非常短小的直線段構(gòu)成)
4、bindtouchmove事件會(huì)在手指觸摸后移動(dòng)時(shí),實(shí)時(shí)返回當(dāng)前狀態(tài)
5、那么可否通過(guò)bindtouchmove 結(jié)合 moveTo ==> lineTo ==> stroke ==> moveTo ==> … 以上一次的結(jié)束為下一次的開(kāi)始這樣的方式來(lái)實(shí)時(shí)渲染直線段合并為一個(gè)近似的曲線

  // 手指觸摸后移動(dòng)	bindtouchmove(event) {let {type, changedTouches} = event;let {x, y} = changedTouches[0];// 上一段終點(diǎn)ctx.lineTo(x, y) // 從最后一點(diǎn)到點(diǎn)(x,y)繪制一條直線。// 繪制ctx.stroke();// 下一段起點(diǎn)ctx.moveTo(x, y) // 設(shè)置繪圖起始坐標(biāo)。},

6、歸納封裝

  // 手指觸摸動(dòng)作開(kāi)始bindtouchstart(event) {this.addPathDrop(event)},// 手指觸摸后移動(dòng)	bindtouchmove(event) {this.addPathDrop(event)},// 手指觸摸動(dòng)作結(jié)束bindtouchend(event) {this.addPathDrop(event)},// 手指觸摸動(dòng)作被打斷,如來(lái)電提醒,彈窗bindtouchcancel(event) {this.addPathDrop(event)},// 添加路徑點(diǎn)addPathDrop(event) {let {ctx, historyImag, canvas} = this.datalet {type, changedTouches} = eventlet {x, y} = changedTouches[0]if(type === 'touchstart') { // 每次開(kāi)始都是一次新動(dòng)作// 最開(kāi)始點(diǎn)ctx.moveTo(x, y) // 設(shè)置繪圖起始坐標(biāo)。} else {// 上一段終點(diǎn)ctx.lineTo(x, y) // 從最后一點(diǎn)到點(diǎn)(x,y)繪制一條直線。// 繪制ctx.stroke();// 下一段起點(diǎn)ctx.moveTo(x, y) // 設(shè)置繪圖起始坐標(biāo)。}},
3、上一步、重繪、提交

主體思路為每一次繪制完成后都通過(guò)wx.canvasToTempFilePath生成圖片,并記錄下來(lái),通過(guò)canvas的drawImage方法將圖片繪制到 canvas 上

五、完整代碼

1、inde.json

{"navigationBarTitleText": "電子簽名","backgroundTextStyle": "dark","pageOrientation": "landscape","disableScroll": true,"usingComponents": {"van-button": "@vant/weapp/button/index","van-toast": "@vant/weapp/toast/index"}
}

2、index.wxml

<!-- index.wxml -->
<view><view class="content" style="padding-left: {{deviceInFo.safeArea.left || 10}}px"><view class="canvas_box"><!-- 定位到canvas畫布的下方作為背景 --><view class="canvas_tips">簽字區(qū)</view><!-- canvas畫布 --><canvas class="canvas_content" type="2d" style='width:{{canvasWidth}}px; height:{{canvasHeight}}px' id="myCanvas" bindtouchstart="bindtouchstart" bindtouchmove="bindtouchmove" bindtouchend="bindtouchend" bindtouchcancel="bindtouchcancel"></canvas></view></view><!-- footer --><view class="footer" style="padding-left: {{deviceInFo.safeArea.left}}px"><van-button plain class="item" block icon="replay" bind:click="overwrite" type="warning">清除重寫</van-button><van-button plain class="item" block icon="revoke" bind:click="prev" type="danger">撤銷</van-button><van-button class="item" block icon="passed" bind:click="confirm" type="info">提交</van-button></view>
</view>
<!-- 提示框組件 -->
<van-toast id="van-toast" />

2、index.less

.content {box-sizing: border-box;width: 100%;height: 100%;padding: 10px;.canvas_box {width: 100%;height: 100%;background-color: #E8E9EC;position: relative;// 定位到canvas畫布的下方作為背景.canvas_tips {position: absolute;left: 0;top: 0;width: 100%;height: 100%;font-size: 80px;color: #E2E2E2;font-weight: bold;display: flex;align-items: center;justify-content: center;}// .canvas_content {//   width: 100%;//   height: 100%;// }}
}
// 底部按鈕
.footer {box-sizing: border-box;padding: 20rpx 0;z-index: 2;background-color: #ffffff;text-align: center;position: fixed;width: 100%;box-shadow: 0 0 15rpx rgba(0, 0, 0, 0.1);left: 0;bottom: 0;display: flex;.item {flex: 1;margin: 0 10rpx;}.scan {width: 80rpx;margin: 0 10rpx;}.moreBtn {width: 150rpx}
}

3、index.js

// index.js
// 獲取應(yīng)用實(shí)例
// import request from "../../request/index";
import Toast from '@vant/weapp/toast/toast';const app = getApp()
Page({data: {// expertId: '', // 專家iddeviceInFo: {}, // 設(shè)備信息canvasWidth: '', // 畫布寬canvasHeight: '', // 畫布高canvas: null, // Canvas 對(duì)象實(shí)例ctx: null, // Canvas 對(duì)象上下文實(shí)例historyImag: [], // 歷史記錄,每一筆動(dòng)作完成后的圖片數(shù)據(jù),用于每一次回退上一步是當(dāng)作圖片繪制到畫布上fileList: [], // 簽名后生成的附件initialCanvasImg: '', // 初始畫布圖,解決非ios設(shè)備重設(shè)置寬高不能清空畫布的問(wèn)題},onReady() {// 獲取可使用窗口的寬高,賦值給Canvas(寬高要減去上下左右padding的20,以及高度要減去footer區(qū)域)wx.createSelectorQuery().select('.footer') // canvas獲取節(jié)點(diǎn).fields({ node: true, size: true }) // 獲取節(jié)點(diǎn)的相關(guān)信息,node:是否返回節(jié)點(diǎn)對(duì)應(yīng)的 Node 實(shí)例,size:是否返回節(jié)點(diǎn)尺寸.exec((res) => {console.log('res', res);// 獲取手機(jī)左側(cè)安全區(qū)域(劉海)const deviceInFo = wx.getSystemInfoSync()const canvasWidth = deviceInFo.windowWidth - 20 - deviceInFo?.safeArea?.left || 0const canvasHeight = deviceInFo.windowHeight - res[0].height - 20this.setData({deviceInFo,canvasWidth,canvasHeight})this.initCanvas('init')})},onLoad(option) {wx.setNavigationBarTitle({title: '電子簽名'})// const {expertId} = option// this.setData({expertId})},// 初始話Canvas畫布initCanvas(type) {let ctx = nulllet canvas = nulllet {historyImag, canvasWidth, canvasHeight, deviceInFo, initialCanvasImg} = this.data// 獲取Canvas畫布以及渲染上下文wx.createSelectorQuery().select('#myCanvas') // canvas獲取節(jié)點(diǎn).fields({ node: true, size: true }) // 獲取節(jié)點(diǎn)的相關(guān)信息,node:是否返回節(jié)點(diǎn)對(duì)應(yīng)的 Node 實(shí)例,size:是否返回節(jié)點(diǎn)尺寸.exec((res) => { // 執(zhí)行所有的請(qǐng)求。請(qǐng)求結(jié)果按請(qǐng)求次序構(gòu)成數(shù)組// Canvas 對(duì)象實(shí)例canvas = res[0].node// Canvas 對(duì)象上下文實(shí)例(動(dòng)畫動(dòng)作繪圖等都是在他的身上完成)ctx = canvas.getContext('2d')// Canvas 畫布的實(shí)際繪制寬高const width = res[0].widthconst height = res[0].height// 獲取設(shè)備像素比const dpr = wx.getWindowInfo().pixelRatio// 初始化畫布大小canvas.width = width * dprcanvas.height = height * dpr// 畫筆的顏色ctx.fillStyle = 'rgb(200, 0, 0)';// 指定了畫筆(繪制線條)操作的線條寬度ctx.lineWidth = 5// 如果存在歷史記錄,則將歷史記錄最新的一張圖片拿出來(lái)進(jìn)行繪制。非ios時(shí)直接加載一張初始的空白圖片if(historyImag.length !== 0 || (deviceInFo.platform !== 'ios' && type !== 'init')) {// 圖片對(duì)象const image = canvas.createImage()// 圖片加載完成回調(diào)image.onload = () => {// 將圖片繪制到 canvas 上ctx.drawImage(image, 0, 0, canvasWidth, canvasHeight)}// 設(shè)置圖片srcimage.src = historyImag[historyImag.length - 1] || initialCanvasImg;}// 縮小/放大圖像ctx.scale(dpr, dpr)this.setData({canvas, ctx})// 保存一張初始空白圖片if(type === 'init') {wx.canvasToTempFilePath({canvas,png: 'png',success: res => {// 生成的圖片臨時(shí)文件路徑const tempFilePath = res.tempFilePaththis.setData({initialCanvasImg: tempFilePath})},})}})},// 手指觸摸動(dòng)作開(kāi)始bindtouchstart(event) {this.addPathDrop(event)},// 手指觸摸后移動(dòng)	bindtouchmove(event) {this.addPathDrop(event)},// 手指觸摸動(dòng)作結(jié)束bindtouchend(event) {this.addPathDrop(event)},// 手指觸摸動(dòng)作被打斷,如來(lái)電提醒,彈窗bindtouchcancel(event) {this.addPathDrop(event)},// 添加路徑點(diǎn)addPathDrop(event) {let {ctx, historyImag, canvas} = this.datalet {type, changedTouches} = eventlet {x, y} = changedTouches[0]if(type === 'touchstart') { // 每次開(kāi)始都是一次新動(dòng)作// 最開(kāi)始點(diǎn)ctx.moveTo(x, y) // 設(shè)置繪圖起始坐標(biāo)。} else {// 上一段終點(diǎn)ctx.lineTo(x, y) // 從最后一點(diǎn)到點(diǎn)(x,y)繪制一條直線。// 繪制ctx.stroke();// 下一段起點(diǎn)ctx.moveTo(x, y) // 設(shè)置繪圖起始坐標(biāo)。}// 每一次結(jié)束或者意外中斷,保存一份圖片到歷史記錄中if(type === 'touchend' || type === 'touchcancel') {// 生成圖片// historyImag.push(canvas.toDataURL('image/png'))wx.canvasToTempFilePath({canvas,png: 'png',success: res => {// 生成的圖片臨時(shí)文件路徑const tempFilePath = res.tempFilePathhistoryImag.push(tempFilePath)this.setData(historyImag)},})}},// 上一步prev() {this.setData({historyImag: this.data.historyImag.slice(0, this.data.historyImag.length - 1)})this.initCanvas()},// 重寫overwrite() {this.setData({historyImag: []})this.initCanvas()},// 提交confirm() {const {canvas, historyImag} = this.dataif(historyImag.length === 0) {Toast.fail('請(qǐng)先簽名后保存!');return}// 生成圖片wx.canvasToTempFilePath({canvas,png: 'png',success: res => {// 生成的圖片臨時(shí)文件路徑const tempFilePath = res.tempFilePath// 保存圖片到系統(tǒng)wx.saveImageToPhotosAlbum({filePath: tempFilePath,})// this.beforeRead(res.tempFilePath)},})},// // 圖片上傳// async beforeRead(tempFilePath) {//   const that = this;//   wx.getImageInfo({//     src: tempFilePath,//     success(imageRes) {//       wx.uploadFile({//         url: '', // 僅為示例,非真實(shí)的接口地址//         filePath: imageRes.path,//         name: 'file',//         header: {token: wx.getStorageSync('token')},//         formData: {//           ext: imageRes.type//         },//         success(fileRes) {//           const response = JSON.parse(fileRes.data);//           if (response.code === 200) {//             that.setData({//               fileList: [response.data]//             })//             that.submit();//           } else {//             wx.hideLoading();//             Toast.fail('附件上傳失敗');//             return false;//           }//         },//         fail(err) {//           wx.hideLoading();//           Toast.fail('附件上傳失敗');//         }//       });//     },//     fail(err) {//       wx.hideLoading();//       Toast.fail('附件上傳失敗');//     }//   })// },// 提交// submit() {//   const {fileList} = this.data//   wx.showLoading({title: '提交中...',})//   request('post', '', {//     fileIds: fileList.map(item => item.id),//   }).then(res => {//     if (res.code === 200) {//       wx.hideLoading();//       Toast.success('提交成功!');//       setTimeout(() => {//         wx.navigateBack({delta: 1});//       }, 1000)//     }//   })// },
})
http://www.risenshineclean.com/news/43231.html

相關(guān)文章:

  • 重慶品牌網(wǎng)站建設(shè)電商自學(xué)網(wǎng)
  • wap手機(jī)網(wǎng)站源碼企業(yè)網(wǎng)站的作用有哪些
  • wordpress 更新很慢微信公眾號(hào)seo
  • 西安做的好的網(wǎng)站公司南昌seo全網(wǎng)營(yíng)銷
  • 怎么創(chuàng)建網(wǎng)站 免費(fèi)的官網(wǎng)設(shè)計(jì)公司
  • 新企業(yè)在哪里做網(wǎng)站好關(guān)鍵詞推廣優(yōu)化排名品牌
  • wordpress文章頁(yè)面菜單優(yōu)化大師win7
  • 女女做的網(wǎng)站目前最新推廣平臺(tái)
  • 南通網(wǎng)站開(kāi)發(fā)招聘按效果付費(fèi)的網(wǎng)絡(luò)推廣方式
  • html5手機(jī)網(wǎng)站開(kāi)發(fā)區(qū)別百度快照推廣
  • 建設(shè)網(wǎng)站必備條件長(zhǎng)春網(wǎng)站建設(shè)推廣
  • 大于二高端網(wǎng)站建設(shè)新手seo入門教程
  • 網(wǎng)站標(biāo)簽怎么做重慶網(wǎng)站網(wǎng)絡(luò)推廣
  • 淄博北京網(wǎng)站建設(shè)手機(jī)百度搜索引擎入口
  • 做網(wǎng)站收費(fèi)標(biāo)準(zhǔn)哪個(gè)平臺(tái)可以免費(fèi)打廣告
  • 網(wǎng)站在建設(shè)時(shí)不容忽略的一些細(xì)節(jié)最權(quán)威的排行榜網(wǎng)站
  • 網(wǎng)站建設(shè)中模板下載武漢百度開(kāi)戶代理
  • 百度搜索不到asp做的網(wǎng)站天津搜狗seo推廣
  • 網(wǎng)站建設(shè)哪個(gè)空間比較好網(wǎng)站怎么優(yōu)化到首頁(yè)
  • 上海簡(jiǎn)站商貿(mào)有限公司seo基礎(chǔ)理論
  • 做任務(wù)傭金網(wǎng)站源碼互聯(lián)網(wǎng)營(yíng)銷培訓(xùn)平臺(tái)
  • 公眾號(hào)編輯 wordpress魔貝課凡seo
  • 聚美優(yōu)品網(wǎng)站怎么做的最新的即時(shí)比分
  • 白糖貿(mào)易怎么做網(wǎng)站廈門seo公司到1火星
  • 外貿(mào)網(wǎng)站建設(shè)設(shè)計(jì)杭州做seo的公司
  • 微信h5免費(fèi)制作網(wǎng)站seo優(yōu)化與推廣招聘
  • 招聘網(wǎng)站怎么做營(yíng)銷軟文代寫平臺(tái)
  • 個(gè)人網(wǎng)站可以做淘寶客杭州網(wǎng)站推廣平臺(tái)
  • 商城網(wǎng)站建站深圳優(yōu)化seo排名
  • 如果做鏡像網(wǎng)站360廣告投放平臺(tái)