pixel-data-js 0.5.0 → 0.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Compressed data format for image processing optimization.
|
|
3
|
+
* Representing an image as a grid of palette indices rather than raw RGBA values
|
|
4
|
+
* significantly reduces memory overhead and optimizes pattern matching logic.
|
|
5
|
+
*/
|
|
6
|
+
export type IndexedImage = {
|
|
7
|
+
/** The width of the image in pixels. */
|
|
8
|
+
width: number,
|
|
9
|
+
/** The height of the image in pixels. */
|
|
10
|
+
height: number,
|
|
11
|
+
/**
|
|
12
|
+
* A flat array of indices where each value points to a color in the palette.
|
|
13
|
+
* Accessible via the formula: `index = x + (y * width)`.
|
|
14
|
+
*/
|
|
15
|
+
data: Int32Array,
|
|
16
|
+
/**
|
|
17
|
+
* A flattened Uint8Array of RGBA values.
|
|
18
|
+
* Every 4 bytes represent one color: `[r, g, b, a]`.
|
|
19
|
+
*/
|
|
20
|
+
palette: Uint8Array,
|
|
21
|
+
/**
|
|
22
|
+
* The specific index in the palette that represents a fully transparent pixel.
|
|
23
|
+
* All pixels with an alpha value of 0 are normalized to this index.
|
|
24
|
+
*/
|
|
25
|
+
transparentPalletIndex: number,
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* Converts standard ImageData into an IndexedImage format.
|
|
30
|
+
* This process normalizes all transparent pixels into a single palette entry
|
|
31
|
+
* and maps all unique RGBA colors to sequential integer IDs.
|
|
32
|
+
* @param imageData - The raw ImageData from a canvas or image source.
|
|
33
|
+
* @returns An IndexedImage object containing the index grid and color palette.
|
|
34
|
+
*/
|
|
35
|
+
export function makeIndexedImage(imageData: ImageData): IndexedImage {
|
|
36
|
+
const width = imageData.width
|
|
37
|
+
const height = imageData.height
|
|
38
|
+
const rawData = imageData.data
|
|
39
|
+
const indexedData = new Int32Array(rawData.length / 4)
|
|
40
|
+
const colorMap = new Map<string, number>()
|
|
41
|
+
const tempPalette: number[] = []
|
|
42
|
+
|
|
43
|
+
const transparentKey = '0,0,0,0'
|
|
44
|
+
const transparentPalletIndex = 0
|
|
45
|
+
|
|
46
|
+
// Initialize palette with normalized transparent color at index 0
|
|
47
|
+
colorMap.set(transparentKey, transparentPalletIndex)
|
|
48
|
+
tempPalette.push(0)
|
|
49
|
+
tempPalette.push(0)
|
|
50
|
+
tempPalette.push(0)
|
|
51
|
+
tempPalette.push(0)
|
|
52
|
+
|
|
53
|
+
for (let i = 0; i < indexedData.length; i++) {
|
|
54
|
+
const r = rawData[i * 4]!
|
|
55
|
+
const g = rawData[i * 4 + 1]!
|
|
56
|
+
const b = rawData[i * 4 + 2]!
|
|
57
|
+
const a = rawData[i * 4 + 3]!
|
|
58
|
+
|
|
59
|
+
let key: string
|
|
60
|
+
if (a === 0) {
|
|
61
|
+
key = transparentKey
|
|
62
|
+
} else {
|
|
63
|
+
key = `${r},${g},${b},${a}`
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
let id = colorMap.get(key)
|
|
67
|
+
|
|
68
|
+
if (id === undefined) {
|
|
69
|
+
id = colorMap.size
|
|
70
|
+
tempPalette.push(r)
|
|
71
|
+
tempPalette.push(g)
|
|
72
|
+
tempPalette.push(b)
|
|
73
|
+
tempPalette.push(a)
|
|
74
|
+
colorMap.set(key, id)
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
indexedData[i] = id
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
const palette = new Uint8Array(tempPalette)
|
|
81
|
+
|
|
82
|
+
return {
|
|
83
|
+
width,
|
|
84
|
+
height,
|
|
85
|
+
data: indexedData,
|
|
86
|
+
transparentPalletIndex,
|
|
87
|
+
palette,
|
|
88
|
+
}
|
|
89
|
+
}
|