我正在使用“反射阴影贴图”在我的游戏引擎中实现全局照明。 RSM有i.a.颜色纹理。为了节省内存。我将24位值打包成8位值。好。我知道怎么收拾它。但是我该如何打开包装呢?我有意创建一个带有8位调色板的一维纹理,有255种不同的颜色。我的8位颜色将是该纹理中的像素索引。 我不知道如何生成这种纹理。 有没有数学方法可以将8位值转换为rgb?
@edit
颜色采用以下格式:
RRR GGG BB
@ EDIT2: 我正在打包我的颜色:
int packed = (red / 32 << 5) + (green / 32 << 2) + (blue / 64);
//the int is actually a byte, c# compiler is bitching if it's byte.
@ EDIT3:
好吧,我觉得我找到了一种方法。告诉我,如果这是错的。
@ edit4这是错误的......
int r = (packed >> 5) * 32;
int g = ((packed >> 2) << 3) * 32;
int b = (packed << 6) * 64;
答案 0 :(得分:5)
在javascript中
编码
encodedData = (Math.floor((red / 32)) << 5) + (Math.floor((green / 32)) << 2) + Math.floor((blue / 64));
解码
red = (encodedData >> 5) * 32;
green = ((encodedData & 28) >> 2) * 32;
blue = (encodedData & 3) * 64;
在解码时,我们使用AND Gate / Operator来提取所需的位并丢弃前导位。使用绿色,我们必须向右移动以丢弃右边的位。
虽然编码Math.floor用于截断小数部分,但如果四舍五入,则会创建大于255的总值,使其成为9位数。
更新1
如果我们将颜色除以32或64,则不能提供准确的结果。
RRRGGGBB
R / G = 3bit,二进制最大值为111,十进制为7。 B = 2bit,最大值是二进制11,十进制为3。
我们应该将R / G除以等于或大于255/7的值,将B除以等于或大于255/3的值。 我们还应该注意,代替Math.floor,我们应该使用Math.round,因为舍入可以得到更准确的结果。
答案 1 :(得分:2)
要将8位[0 - 255]值转换为3位[0,7],0不是问题,但记住255应转换为7,因此公式应为Red3 = Red8 * 7/255。 / p>
将24位颜色转换为8位,
8bit Color = (Red * 7 / 255) << 5 + (Green * 7 / 255) << 2 + (Blue * 3 / 255)
要反转,
Red = (Color >> 5) * 255 / 7
Green = ((Color >> 2) & 0x07) * 255 / 7
Blue = (Color & 0x03) * 255 / 3