iT邦幫忙

第 11 屆 iT 邦幫忙鐵人賽

DAY 3
1
Modern Web

用 Javascript 當個影像魔術師系列 第 3

Day 03 - 圖片格式簡介(RGBA)

獲取圖片

在上一章節中,我們已經成功將圖片繪畫至 Canvas 上,而接下來就是該如何取得上面的資訊了

這次我們調用渲染環境的另一個方法,getImageData,這個方法使用了四個參數,第一、二個分別是代表起始位置,第三、四個則是代表要獲取的寬高。因為我們是要直接獲得整張圖,所以直接帶入我們在之前用的寬高。

const pixelData = context.getImageData(0, 0, cw, ch)

透過這個方式我們將會拿到 ImageData ,這個物件裡面有三個屬性,分別是 datawidthheight,後兩個代表拿到的寬高,而 data 會發現看起來像個一般的陣列,但會發現顯示上又有點不太一樣,會出現 Uint8ClampedArray,而這個一般我們常見的陣列又有何區別呢

TypedArray

TypedArray 是為了更有效的處理數據而產生出的格式,相較於其他陣列,TypedArray 面所儲存的是二進制數組,裡面的值都會統一類型,所以相較於一般的陣列在傳遞上會更有效率。而要注意的地方是,TypedArray 可以使用原生陣列的方法但不是所有陣列的原生方法都適用在TypedArray,在使用上請注意。

類型 占據內存( bytes ) 範圍
Int8 1 -128 to 127
Uint8 1 0 to 255
Uint8Clamp 1 0 to 255
Int16 2 -32768 to 32767
Uint16 2 0 to 65535

RGBA格式

ImageData 裡,每一個像素以四個通道來代表,也就是 R ( 紅色 )、G ( 綠色 )、B ( 藍色 )、A ( 透明度 ),所以在 data 裡面的長度就會等於 width * height * 4

所以假設我們今天丟進去的圖片只有三個像素如下圖 ( 請想像正常來說是連在一起的 )

也就是寬高為 3 、 1,在最後獲得到的 Uint8ClampedArray 總長度為 3 * 1 * 4,而值會呈現如下,四個連續數值代表 RGBA 也代表一個像素。

[

255, 0, 0, 255,  // 第一個像素,紅色
0, 255, 0, 255,  // 第二個像素,綠色
0, 0, 255, 255,  // 第三個像素,藍色

]

而每個通道的範圍都在 0 ~ 255間。所以也就是 Uint8ClampedArray 的範圍。而跟 Uint8Array 最大的差別就是當超過 0 ~ 255 範圍區間的時候,Uint8ClampedArray 會將超過的數值找到最近的整數。例如

const test = new Uint8ClampedArray([30, -45, 299]);
console.log(test[0]); // 30 
console.log(test[1]); // 0
console.log(test[2]); // 255

小結

今天瞭解從 Canvas 獲取的圖片格式,明天可以開始進入到畫面的部份了


上一篇
Day 02 - Canvas 簡介
下一篇
Day 04 - 圖片資訊
系列文
用 Javascript 當個影像魔術師30

尚未有邦友留言

立即登入留言