canvas效能-drawImage渲染圖片

Mr.蘇發表於2021-01-25

canvas效能-繪製圖片

canvas繪製圖片

一般我們繪製圖片會用到的方法是drawImageputImageData,還有作為測試環境使用的createPattern

drawImage

描述:

使用方式:

ctx.drawImage(image,sx,sy,swidth,sheight,x,y,width,height)
  • image的型別:
    • HTMLImageElement:這些圖片是由Image()函式構造出來的,或者任何的img元素
    • HTMLVideoElement:用一個HTML的video元素作為你的圖片源,可以從視訊中抓取當前幀作為一個影像
    • HTMLCanvasElement:可以使用另一個canvas元素作為你的圖片源
    • ImageBitmap:這是一個高效能的點陣圖,可以低延遲地繪製,它可以從上述的所有源以及其它幾種源中生成
  • sx:可選。開始剪下的 x 座標位置
  • sy:可選。開始剪下的 y 座標位置
  • swidth:可選。被剪下影像的寬度
  • sheight:可選。被剪下影像的高度
  • x:在畫布上放置影像的 x 座標位置
  • y:在畫布上放置影像的 y 座標位置
  • width:可選。要使用的影像的寬度。(伸展或縮小影像)
  • height:可選。要使用的影像的高度。(伸展或縮小影像)

putImageData

描述: Canvas 2D API 將資料從已有的 ImageData 物件繪製到點陣圖的方法。 如果提供了一個繪製過的矩形,則只繪製該矩形的畫素。此方法不受畫布轉換矩陣的影響。

使用方式:

ctx.putImageData(imageData, dx, dy, dirtyX, dirtyY, dirtyWidth, dirtyHeight)
  • ImageData:包含畫素值的陣列物件
  • dx:源影像資料在目標畫布中的位置偏移量(x 軸方向的偏移量)
  • dy:源影像資料在目標畫布中的位置偏移量(y 軸方向的偏移量)
  • dirtyX:可選 在源影像資料中,矩形區域左上角的位置。預設是整個影像資料的左上角(x 座標)
  • dirtyY:可選 在源影像資料中,矩形區域左上角的位置。預設是整個影像資料的左上角(y 座標)
  • dirtyWidth:可選 在源影像資料中,矩形區域的寬度。預設是影像資料的寬度
  • dirtyHeight:可選 在源影像資料中,矩形區域的高度。預設是影像資料的高度。

createPattern

描述:指定的方向內重複指定的元素,元素可以是圖片、視訊,或者其他 canvas 元素,被重複的元素可用於繪製/填充矩形、圓形或線條等等。

使用方式:

ctx.fillStyle = ctx.createPattern(img,"repeat")
ctx.fill();

測試繪製耗時

測試圖片尺寸為(500x500)和(1920x1080)的jpg圖片

drawImage

首先測試的是drawImage方法,通過繪製同一張圖片不同的資源型別下的耗時

Image型別

  • 在空白canvas情況下渲染該圖片耗時:0.01ms左右
  • 在使用了createPattern填充了canvas作為背景的情況下渲染該圖片耗時:0.01ms左右

ImageBitmap型別

  • 在空白canvas情況下渲染該圖片耗時:1ms左右,(1920*1080)是1.8ms左右
  • 在使用了createPattern填充了canvas作為背景的情況下渲染該圖片耗時:0.01ms左右,(1920*1080)是2ms左右

HTMLCanvasElement型別

  • 在空白canvas情況下渲染該圖片耗時:0.01ms左右
  • 在使用了createPattern填充了canvas作為背景的情況下渲染該圖片耗時:12ms左右,(1920*1080)是14ms左右

putImageData

  • 在空白canvas情況下渲染該圖片耗時:1ms左右
  • 在使用了createPattern填充了canvas作為背景的情況下渲染該圖片耗時:2ms左右
渲染圖片方式 空白canvas下渲染耗時 圖片尺寸(500*500) 使用createPattern鋪滿下渲染耗時 圖片尺寸(500*500) 空白canvas下渲染耗時 圖片尺寸(1920*1080) 使用createPattern鋪滿下渲染耗時 圖片尺寸(1920*1080)
drawImage(Image) 0.01ms 0.01ms 0.01ms 0.01ms
drawImage(ImageBitmap) 0.01ms 0.01ms 0.01ms 0.01ms
drawImage(HTMLCanvasElement) 0.01ms 12ms 0.01ms 14ms
putImageData 1ms 2ms 1.8ms 3ms

結論

  1. 由上面的測試結果可以看出在空白canvas下渲染圖片,除了putImageData剩下的效能是一致的即Image = ImageBitmap = HTMLCanvasElement > putImageData。
  2. 而使用了createPattern平鋪作為背景的情況下Image = ImageBitmap > putImageData > HTMLCanvasElement
  3. 渲染圖片尺寸大小一般情況下對drawImage(Image)和drawImage(ImageBitmap)的影響較小,而且效能優越。
  4. createPattern鋪滿的情況下drawImage(HTMLCanvasElement)的效能最差和drawImage(Image)能達到3個數量級的差距
  5. drawImage(HTMLCanvasElement)在空白canvas下效能也很優越
  6. putImageData的效能處於中等,使用createPattern鋪滿背景的情況下會有一定影響,不過不是太大

所以可以不使用使用createPattern鋪滿背景的情況下儘量不要使用,可以使用多層canvas,不必要的層級可以減少重繪。或者將平鋪的背景轉為Image物件使用。

當然以上的結論為我個人開發時的遇到的問題的總結,如果有誤請提出。因為樣本數量和圖片格式並沒有達到太多。

相關文章