微信小程序使用canvas畫(huà)圖保存圖片到手機(jī)相冊(cè)代碼示例
微信小程序要實(shí)現(xiàn)使用canvas繪制一個(gè)圖,然后保存到手機(jī)相冊(cè)
**最終效果:**實(shí)現(xiàn)生成以下圖片

一、初始化canvas
// wxml頁(yè)面設(shè)置canvas標(biāo)簽
<canvas style="width: {{windowW}}px; height: {{windowH}}px;" disable-scroll='true' canvas-id="myCanvas" wx:if="{{showCanvas}}"></canvas>
// js頁(yè)面初始化canvas
data: {
ctx: '',
details: '',
windowW: 375*3,
windowH: 265*3,
ratio:3,
showCanvas:false
},
onLoad(options) {
this.setData({
ctx: wx.createCanvasContext('myCanvas'),
showCanvas:true
})
},
二、繪制canvas
// 繪制一個(gè)準(zhǔn)考證并下載到手機(jī)相冊(cè)
getsaves(){
var that = this;
let rat = 3;
that.data.ctx.setFontSize(8*rat);
that.data.ctx.setFillStyle('#080808');
that.data.ctx.fillText('山東省第六屆中小學(xué)生作文大賽決賽', 28*rat, 29*rat);
that.data.ctx.setFontSize(8*rat);
that.data.ctx.fillText('準(zhǔn)考證', 81*rat, 59*rat);
that.data.ctx.setFontSize(6*rat);
that.data.ctx.fillText('考試時(shí)間:' + '10月18日(周五)上午9:00-11:00', 35*rat, 78*rat);
that.data.ctx.fillText('考試地點(diǎn):山東師范大學(xué)附屬小學(xué)', 35*rat, 93*rat);
that.data.ctx.fillText('濟(jì)南市歷下區(qū)山師北街1號(hào)', 66*rat, 104*rat);
// that.data.ctx.fillText(that.data.details.cityName=='濟(jì)南市'?'考試地點(diǎn):山東師范大學(xué)附屬小學(xué)':'考試地點(diǎn):臨沂商城實(shí)驗(yàn)學(xué)校', 26*rat, 93*rat);
// that.data.ctx.fillText(that.data.details.cityName=='濟(jì)南市'?'濟(jì)南市歷下區(qū)山師北街1號(hào)':'臨沂市蘭山區(qū)蘭山街道工業(yè)大道59號(hào)', 56*rat, 104*rat);
that.data.ctx.setFillStyle('#444444');
that.data.ctx.fillText('準(zhǔn)考證號(hào)', 43*rat, 128*rat);
that.data.ctx.fillText('考生姓名', 43*rat, 144*rat);
that.data.ctx.fillText('考生學(xué)校', 43*rat, 160*rat);
that.data.ctx.fillText('考生組別', 43*rat, 176*rat);
that.data.ctx.fillText('考場(chǎng)號(hào)', 43*rat, 192*rat);
that.data.ctx.fillText('座位號(hào)', 43*rat, 208*rat);
that.data.ctx.setFillStyle('#000000');
that.data.ctx.fillText('2023005020340', 81*rat, 128*rat);
that.data.ctx.fillText('張三', 81*rat, 144*rat);
that.data.ctx.fillText('蔣莊礦區(qū)學(xué)校', 81*rat, 160*rat);
that.data.ctx.fillText('初中組', 81*rat, 176*rat);
that.data.ctx.fillText('--', 81*rat, 192*rat);
that.data.ctx.fillText('--', 81*rat, 208*rat);
that.data.ctx.setFillStyle('#080808');
that.data.ctx.setFontSize(5*rat);
that.data.ctx.fillText('請(qǐng)妥善保管,憑有效身份證件(身份證、戶口本、護(hù)照、', 35*rat, 226*rat);
that.data.ctx.fillText('社保卡、學(xué)生證等)入場(chǎng)考試。', 35*rat, 238*rat);
that.data.ctx.setFontSize(8*rat);
that.data.ctx.fillText('考生守則', 255*rat, 29*rat);
const text1 = ' 一、考生必須自覺(jué)服從監(jiān)考員等考試工作人員管理,不得以任何理由妨礙監(jiān)考員等考試工作人員履行職責(zé),不得擾亂考場(chǎng)及其他考試工作地點(diǎn)的秩序。二、考生憑準(zhǔn)考證、身份證(學(xué)生證、戶口簿)按規(guī)定時(shí)間、地點(diǎn)參加考試。三、考生人場(chǎng),除書(shū)寫(xiě)用0.5mm黑色簽字筆外,其他任何物品不準(zhǔn)帶入考場(chǎng)。嚴(yán)禁攜帶各種通訊工具(如無(wú)線耳機(jī)、移動(dòng)電話及其他無(wú)線接收、傳送設(shè)備等)、手表、電子存儲(chǔ)記憶錄放設(shè)備以及涂改液、修正帶等物品進(jìn)人考場(chǎng)??紙?chǎng)內(nèi)不得自行傳遞文具、用品等。四、考生入場(chǎng)后,對(duì)號(hào)入座,將準(zhǔn)考證等證件放在課桌左上角以便核驗(yàn),考生領(lǐng)到答題和試卷后,應(yīng)檢查答題卡和試卷是否有重印、漏印、字跡不清等印刷質(zhì)量問(wèn)題或缺頁(yè)現(xiàn)象,如有,請(qǐng)立即舉手報(bào)告,否則在開(kāi)考一段時(shí)間后,考生如發(fā)現(xiàn)上述問(wèn)題,由此延誤的考試時(shí)不予彌補(bǔ)??忌鷳?yīng)在指定位置和規(guī)定的時(shí)間內(nèi)準(zhǔn)確清楚地填寫(xiě)畢業(yè)學(xué)校、姓名準(zhǔn)考證號(hào)、座號(hào)等欄目。五、開(kāi)考信號(hào)發(fā)出后才能開(kāi)始答題。六、開(kāi)考15 分鐘后不準(zhǔn)人場(chǎng)。七、在考場(chǎng)內(nèi)須保持安靜,不準(zhǔn)喧嘩,不準(zhǔn)交頭接耳、左顧右盼,不準(zhǔn)將試題、草稿紙帶出考場(chǎng)。八、考試終了信號(hào)發(fā)出后,考生應(yīng)立即停止答卷,并按試題、草稿紙自下而上的順序排放好,坐在座位上,等候考員查收,無(wú)誤后,根據(jù)監(jiān)考員指令依次離開(kāi)考場(chǎng)。九、如不遵守考場(chǎng)紀(jì)律,不服從考試工作人員管理,有違紀(jì)、作弊等行為的,將按照《國(guó)家教育考試違規(guī)處理辦法》進(jìn)行處理。';
that.drawText(that.data.ctx, text1, 185*rat, 49*rat, 30*rat,165*rat); // 假設(shè)每行的最大寬度為300像素
that.data.ctx.setStrokeStyle("#646464");
that.data.ctx.setLineWidth(1);
that.data.ctx.rect(35*rat, 118*rat, 127*rat, 96*rat);
that.data.ctx.stroke()
that.data.ctx.beginPath(); //創(chuàng)建一條路徑
that.data.ctx.moveTo(35*rat, 133*rat); //描述路徑的起點(diǎn)為手指觸摸的x軸和y軸
that.data.ctx.lineTo(162*rat, 133*rat); //繪制一條直線,終點(diǎn)坐標(biāo)為手指觸摸結(jié)束后的x軸和y軸
that.data.ctx.moveTo(35*rat, 149*rat); //描述路徑的起點(diǎn)為手指觸摸的x軸和y軸
that.data.ctx.lineTo(162*rat, 149*rat); //繪制一條直線,終點(diǎn)坐標(biāo)為手指觸摸結(jié)束后的x軸和y軸
that.data.ctx.moveTo(35*rat, 165*rat); //描述路徑的起點(diǎn)為手指觸摸的x軸和y軸
that.data.ctx.lineTo(162*rat, 165*rat); //繪制一條直線,終點(diǎn)坐標(biāo)為手指觸摸結(jié)束后的x軸和y軸
that.data.ctx.moveTo(35*rat, 181*rat); //描述路徑的起點(diǎn)為手指觸摸的x軸和y軸
that.data.ctx.lineTo(162*rat, 181*rat); //繪制一條直線,終點(diǎn)坐標(biāo)為手指觸摸結(jié)束后的x軸和y軸
that.data.ctx.moveTo(35*rat, 197*rat); //描述路徑的起點(diǎn)為手指觸摸的x軸和y軸
that.data.ctx.lineTo(162*rat, 197*rat); //繪制一條直線,終點(diǎn)坐標(biāo)為手指觸摸結(jié)束后的x軸和y軸
that.data.ctx.moveTo(73*rat,118*rat);
that.data.ctx.lineTo(73*rat, 214*rat); // 繪制一條直線到終點(diǎn)
that.data.ctx.stroke();
that.data.ctx.draw(true, function () {
that.daochu();
});
},
三、封裝文字換行縮進(jìn)
// 由于右側(cè)文字較多,需要縮進(jìn)和自動(dòng)換行
drawText(ctx, str, leftWidth, initHeight, titleHeight, canvasWidth) {
ctx.setFontSize(16);
let lineWidth = 0;
let lastSubStrIndex = 0; // 每次開(kāi)始截取的字符串的索引
const indentWidth = 20; // 定義縮進(jìn)寬度
let shouldIndent = false; // 是否需要縮進(jìn)
for (let i = 0; i < str.length; i++) {
const charWidth = ctx.measureText(str[i]).width;
lineWidth += charWidth;
// 檢查是否需要換行
if (lineWidth > canvasWidth - indentWidth || str[i] === '。') {
// 處理當(dāng)前行文本
let lineText = str.substring(lastSubStrIndex, i + 1);
if (shouldIndent) {
lineText = ' '.repeat(indentWidth / ctx.measureText(' ').width) + lineText;
shouldIndent = false; // 只在句號(hào)后的一行縮進(jìn)
}
ctx.fillText(lineText, leftWidth, initHeight); // 繪制文本
initHeight += 22; // 16為字體的高度
lineWidth = 0; // 新行開(kāi)始時(shí)寬度為0
lastSubStrIndex = i + 1; // 更新開(kāi)始截取的索引
// 如果遇到句號(hào),設(shè)置需要縮進(jìn)的標(biāo)志
if (str[i] === '。') {
shouldIndent = true;
}
// 更新leftWidth并考慮縮進(jìn)
leftWidth = leftWidth;
}
}
// 處理最后一行文本
if (lastSubStrIndex < str.length) {
let lineText = str.substring(lastSubStrIndex);
if (shouldIndent) {
lineText = ' '.repeat(indentWidth / ctx.measureText(' ').width) + lineText;
}
ctx.fillText(lineText, leftWidth, initHeight);
}
// 標(biāo)題border-bottom 線距頂部距離
titleHeight += 10;
return titleHeight;
},總結(jié)
到此這篇關(guān)于微信小程序使用canvas畫(huà)圖保存圖片到手機(jī)相冊(cè)的文章就介紹到這了,更多相關(guān)微信小程序canvas畫(huà)圖保存圖片內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
JavaScript中的常見(jiàn)問(wèn)題解決方法(亂碼,IE緩存,代理)
這篇文章主要是對(duì)JavaScript中的常見(jiàn)問(wèn)題解決方法(亂碼,IE緩存,代理)進(jìn)行了詳細(xì)的分析介紹,需要的朋友可以過(guò)來(lái)參考下,希望對(duì)大家有所 幫助2013-11-11
Javascript四舍五入Math.round()與Math.pow()使用介紹
本文為大家介紹下Javascript中的四舍五入Math.round()與Math.pow()的使用,感興趣的朋友不要錯(cuò)過(guò)2013-12-12
多種js圖片預(yù)加載實(shí)現(xiàn)方式分享
這篇文章主要為大家詳細(xì)介紹了多種js圖片預(yù)加載實(shí)現(xiàn)方式,包括html標(biāo)簽或css加載圖片、純js實(shí)現(xiàn)預(yù)加載,感興趣的小伙伴們可以參考一下2016-02-02
關(guān)于JS Lodop打印插件打印Bootstrap樣式錯(cuò)亂問(wèn)題的解決方案
關(guān)于Lodop打印是個(gè)很牛的打印插件,但是打印Bootstrap的樣式的時(shí)候就容易錯(cuò)亂,下面通過(guò)本文給大家分享下這方面的問(wèn)題2016-12-12
讓javascript加載速度倍增的方法(解決JS加載速度慢的問(wèn)題)
這篇文章主要介紹了讓javascript加載速度倍增的方法,通過(guò)document.write輸出js解決廣告加載速度慢的問(wèn)題,需要的朋友可以參考下2014-12-12
javascript 獲取網(wǎng)頁(yè)標(biāo)題
js獲取網(wǎng)頁(yè)標(biāo)題2008-04-04
解決JS使用fill()進(jìn)行數(shù)組填充遇到的問(wèn)題
最近在做算法題時(shí),遇到需要?jiǎng)?chuàng)建二維數(shù)組并進(jìn)行初始化的情況,剛開(kāi)始我使用的是 new Array(n).fill(new Array(n).fill('.')) 進(jìn)行二維數(shù)組的初始化,但無(wú)論怎樣我都通不過(guò)測(cè)試用例,所以本文就給大家詳細(xì)的介紹了如何解決這類問(wèn)題以及將js中的fill(方法重學(xué)一下2023-09-09
微信小程序 TLS 版本必須大于等于1.2問(wèn)題解決
這篇文章主要介紹了微信小程序 TLS 版本必須大于等于1.2問(wèn)題解決的相關(guān)資料,需要的朋友可以參考下2017-02-02

