7. ETC1 圧縮テクスチャのフォーマット解説

ETC(Ericsson Texture Compression)フォーマットで圧縮された ETC1 圧縮テクスチャは、ハードウェアでの展開に対応していますので、通常のテクスチャに比べて高速に処理することができます。さらに、24 bit カラー画像(RGB8)を 4x4 テクセルのブロックごとにわずか 8 バイト(64 bit)に圧縮することができるため、テクスチャで使用するメモリの削減も期待できます。しかし、ブロック内で使われている色が似たような色であることを利用した圧縮方法のため、風景や人物をカメラで撮影した画像の圧縮には向いていますが、赤と青のように RGB 各成分の値が極端に違う色が同じブロック内に存在する画像の圧縮には向いていません。

3DS 独自の仕様として、テクセルごとに 4 bit のアルファ値を付加したフォーマット(合計 128 bit)に対応しています。

この章では、ETC1 圧縮テクスチャのフォーマットを解説し、3DS で使用するために必要なフォーマットの変換についても説明します。

7.1. ETC フォーマット

ETC フォーマットは、4x4 テクセルを 4x2 または 2x4 テクセルで分割したサブブロック単位で、基準となる RGB 値(ベースカラー)と差分を表すテーブルを持っています。フォーマットには個別モード(Individual mode)と差分モード(Differential mode)の 2 種類が存在しますが、その違いは前半の 32 bit に含まれているベースカラーのフォーマットだけです。どちらのフォーマットも後半の 32 bit に違いはなく、ベースカラーの決定以外で展開のアルゴリズムにも違いはありません。

以下に ETC1 圧縮テクスチャのビットレイアウトを示します。データの並びとしては、アルファチャンネルがカラーチャンネルの前に配置されます。

図 7-1. ETC1 圧縮テクスチャのビットレイアウト

7.1.1. テクセルの配置とブロックの分割

後半の 32 bit はさらに MSB と LSB の 16 bit ずつの領域に分かれています。各領域の最下位ビットから最上位ビットの並びは、左上のテクセルから縦方向に右下のテクセルと対応しています。つまり、最下位ビット(bit 0, 16)が左上に配置されたテクセルに対応し、そこから下方向に上位のビットが対応していきます。下端に到達したら、右隣の列の上端から下端に向かって対応し、最上位ビット(bit 15, 31)は右下のテクセルに対応しています。

Flipbit(bit 32)の値によって、ブロックは縦(2x4)または横(4x2)に分割されます。分割された 8 テクセルをサブブロックと呼び、左または上にあるサブブロックをサブブロック 1、右または下にあるサブブロックをサブブロック 2 とします。ブロックの分割方法によってテクセルの配置順は変化しません。

図 7-2. テクセルとサブブロックの配置

Texel layout Sub block layout Sub block 1 Sub block 2 Flipbit

7.1.2. ベースカラーの決定

ベースカラーはサブブロックごとに決定されますが、Diffbit(bit 33)の値によってフォーマットとベースカラーの決定方法に違いがあります。

Diffbit が 0 のときは個別モード(Individual mode)となり、サブブロックごとに R、G、B の各成分が 4 bit ずつ割り当てられています。サブブロック 1 が R1/G1/B1、サブブロック 2 が R2/G2/B2 です。ベースカラーは、この 4 bit を連結して 8 bit に拡張した値(17 倍)です。R1 が 1001b(9)のとき、サブブロック 1 のベースカラーの赤成分は 10011001b(153)となります。

Diffbit が 1 のときは差分モード(Differential mode)となり、サブブロック 1 には R、G、B の各成分が 5 bit ずつ割り当てられ、サブブロック 2 にはサブブロック 1 の 5 bit との差分値として各成分 3 bit が割り当てられています。サブブロック 1 が R1' / G1' / B1'、サブブロック 2 が R1' + dR2 / G1' + dG2 / B1' + dB2 です。サブブロック 1 のベースカラーは、5 bit に上位 3 bit を連結して 8 ビットに拡張した値(8.25倍)です。サブブロック 2 のベースカラーは、5 bit に 2 の補数表現で表された 3 bit の差分値(+3 ~ -4)を加算した結果をサブブロック 1 と同様に拡張した値です。R1' が 11001b(25)、dR2 が 100b(-4)のとき、サブブロック 1 のベースカラーの赤成分は 11001110b(206)、サブブロック 2 のベースカラーの赤成分は 11001b(25)- 100b(4)= 10101b(21)を拡張した値のため 10101101b(173)となります。差分値を加算した結果が 0 ~ 31 の範囲内に収まらない組み合わせは動作が不定となりますので、圧縮時にそのような組み合わせが発生しないようにしなければなりません。

表 7-1. 個別モードでのビット列と拡張後の値の対応
ビット列 ビット列 ビット列 ビット列
0000b 0 0100b 68 1000b 136 1100b 204
0001b 17 0101b 85 1001b 153 1101b 221
0010b 34 0110b 102 1010b 170 1110b 238
0011b 51 0111b 119 1011b 187 1111b 255
表 7-2. 差分モードでのビット列と拡張後の値および差分を考慮した値の対応
ビット列

100b
(-4)

101b
(-3)

110b
(-2)

111b
(-1)

000b
(0)

001b
(+1)

010b
(+2)

011b
(+3)

00000b 0 - - - - 0 8 16 24
00001b 8 - - - 0 8 16 24 33
00010b 16 - - 0 8 16 24 33 41
00011b 24 - 0 8 16 24 33 41 49
00100b 33 0 8 16 24 33 41 49 57
00101b 41 8 16 24 33 41 49 57 66
00110b 49 16 24 33 41 49 57 66 74
00111b 57 24 33 41 49 57 66 74 82
01000b 66 33 41 49 57 66 74 82 90
01001b 74 41 49 57 66 74 82 90 99
01010b 82 49 57 66 74 82 90 99 107
01011b 90 57 66 74 82 90 99 107 115
01100b 99 66 74 82 90 99 107 115 123
01101b 107 74 82 90 99 107 115 123 132
01110b 115 82 90 99 107 115 123 132 140
01111b 123 90 99 107 115 123 132 140 148
10000b 132 99 107 115 123 132 140 148 156
10001b 140 107 115 123 132 140 148 156 165
10010b 148 115 123 132 140 148 156 165 173
10011b 156 123 132 140 148 156 165 173 181
10100b 165 132 140 148 156 165 173 181 189
10101b 173 140 148 156 165 173 181 189 198
10110b 181 148 156 165 173 181 189 198 206
10111b 189 156 165 173 181 189 198 206 214
11000b 198 165 173 181 189 198 206 214 222
11001b 206 173 181 189 198 206 214 222 231
11010b 214 181 189 198 206 214 222 231 239
11011b 222 189 198 206 214 222 231 239 247
11100b 231 198 206 214 222 231 239 247 255
11101b 239 206 214 222 231 239 247 255 -
11110b 247 214 222 231 239 247 255 - -
11111b 255 222 231 239 247 255 - - -

7.1.3. 差分テーブルとテクセルカラーの決定

決定したベースカラーに対して、差分テーブルから選択した差分値を加算した結果が最終的にテクセルカラーとなります。

差分テーブルはサブブロックごとに Table codeword(Table CW)で指定します。指定には、サブブロック 1 が Table CW1(bit 37 ~ 39)を、サブブロック 2 が Table CW2(bit 34 ~ 36)を使い、その値は 3 bit なので 8 種類から選択することができます。差分テーブルには 4 つの差分値が決められており、MSB と LSB の組み合わせでテクセルごとの差分値に使う値が決まります。選択された差分値はベースカラーの RGB 成分すべてに加算され、加算された結果は 0 ~ 255 の範囲にクランプされます。例えば、差分テーブルが 011b、MSB が 1、LSB が 1 のときは -42 がベースカラーの全成分に加算され、ベースカラーを(33, 198, 99)とするとテクセルカラーは(0, 156, 57)となります。

表 7-3. Table codeword、MSB、LSB と差分値の対応
Table codeword MSB=1
LSB=1
MSB=1
LSB=0
MSB=0
LSB=0
MSB=0
LSB=1
000b -8 -2 +2 +8
001b -17 -5 +5 +17
010b -29 -9 +9 +29
011b -42 -13 +13 +42
100b -60 -18 +18 +60
101b -80 -24 +24 +80
110b -106 -33 +33 +106
111b -183 -47 +47 +183

7.2. PICA ネイティブフォーマットでの圧縮テクスチャ

3DS で ETC1 圧縮テクスチャを使用する場合、そのフォーマットは PICA ネイティブフォーマットでなければなりません。PICA ネイティブフォーマットは OpenGL ES の標準仕様とは、テクセルの参照開始座標やブロックの並び、バイトオーダーが異なります。

7.2.1. V フリップ

OpenGL ES ではテクセルの参照開始座標は(u, v)=(0.0, 0.0)ですが、3DS では(u, v)=(0.0, 1.0)となっています。そのため、テクスチャイメージを圧縮する前に v 座標方向のフリップ(V フリップ)を適用しなければなりません。

7.2.2. ブロックフォーマット

ETC1 圧縮テクスチャでは 4x4 テクセルのブロックを u、v 方向に 2 つずつ、8x8 テクセルをメタブロックとして定義しています。メタブロック内ではジグザグにブロックが配置され、メタブロックは u 方向に連続して配置されます。

図 7-3. ETC1 圧縮テクスチャのブロック参照順序

Original u v 0.0 1.0 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63

7.2.3. バイトオーダー

3DS では、エンディアンの関係で OpenGL ES とはデータの並び(バイトオーダー)が異なっています。ビットレイアウトを実際のバイトの並びで見てみると、以下のようなレイアウトとなっています。

図 7-4. 実際のバイトオーダーで見たビットレイアウト

Color channel In both cases Diffbit +0 byte +1 byte +2 byte +3 byte Least significant pixel index bits (LSB) Most significant pixel index bits (MSB) Individual mode +4 byte +5 byte +6 byte +7 byte TableCW1 TableCW2 Flipbit BaseColor1 BaseColor2 B1 B2 G1 G2 R1 R2 DiffColor2 B1' dB2 G1' dG2 R1' dR2 Alpha channel

カラーチャンネルのデータは 8 バイト単位でバイトスワップが行われますが、アルファチャンネルのデータはバイトスワップが行われません。また、アルファチャンネルがカラーチャンネルの前に配置されることに変わりはありません。