最近做了一個生成海報的項目,有個需求需要畫出圖片。
我個人的想法是生成的圖片像image的mode模式中的aspectFill顯示的圖片那樣,“縮放模式,保持縱橫比縮放圖片,只保證圖片的短邊能完全顯示出來。也就是說,圖片通常只在水平或垂直方向是完整的,另一個方向將會發生截取。”
也就是說保證圖片的短邊顯示出來,超過的部分會被截取掉,圖片不會變形
翻看了小程序文檔的CanvasContext.drawImage。然後整理了一下以下的代碼,此代碼只爲了說明CanvasContext.drawImage
wxml:
<canvas style="width:300px;height:300px" canvas-id="actReview"></canvas>
js中的生成圖片的代碼如下:
let ctx = wx.createCanvasContext('actReview')
let img = {
url:'/static/images/img-actImage.png'
}
// 取得圖片的寬高
wx.getImageInfo({
src:img.url,
success (res) {
// 繪製白色背景
ctx.setFillStyle('#fff')
ctx.fillRect(0, 0, 300, 300)
let imgX = 50 //圖片在畫布上的x軸座標
let imgY = 50 //圖片在畫布上的y軸座標
let imgW = 200 //圖片在畫布上的寬度
let imgH = 200 //圖片在畫布上的高度
let visibleW = res.width//截取的圖片的寬度
let visibleH = res.height//截取的圖片的高度
let visibleX = null // 所截取的圖片的x軸座標
let visibleY = null // 所截取的圖片的y軸座標
let imgBili = imgW / imgH
let visibleBili = visibleW / visibleH
if(imgBili < visibleBili){
let newW = (imgH / visibleH) * visibleW
const bili = newW / visibleW
visibleX = Math.abs(imgW - newW) / 2 / bili
visibleY = 0
visibleW = imgW * visibleH / imgH
}else {
visibleX = 0
let newH = (imgW * visibleH) / visibleW
const bili = newH / visibleH
visibleY = Math.abs(imgH - newH) /2 / bili
visibleH = visibleW * imgH / imgW
}
/**
* ctx.drawImage(
* 圖片的url,
* 所截取的圖片的X軸座標,
* 所截取的圖片的Y軸座標,
* 所截取的圖片的寬度,
* 所截取的圖片的高度,
* 圖片在畫布的X軸座標,
* 圖片在畫布的Y軸座標,
* 圖片在畫布的寬度,
* 圖片在畫布的高度)
*/
ctx.drawImage(img.url, visibleX, visibleY, visibleW, visibleH,imgX, imgY, imgW, imgH)
ctx.draw()
},
fail (e) {
console.log(e)
}
})
生成的效果圖(紅色框框部分):
圖片原圖: