24位色彩空间中是否存在所有8位颜色?如果是这样如何映射?

时间:2013-07-18 16:12:01

标签: colors

8位颜色深度有256种颜色。 24位颜色深度有16,777,216种颜色。 8位空间中的每种颜色与24位空间中的颜色之间是否存在直接映射?我认为这个问题的答案是肯定的,但对this answer的评论表明映射只是一个近似值。

我想要做的是通过指定24位RGB值在24位颜色空间中创建8位颜色的调色板。我想我可以使用这个(明显破坏的)逻辑来做到这一点:

3位红色== 8个唯一值红色,0-7

3位为绿色== 8个唯一值为绿色,0-7

2位为蓝色== 4个唯一值为蓝色,0-3

255/8 = 32表示红色和绿色增量值

255/4 = 64表示蓝色增量值

{
    "Red": [0,31,63,95,127,159,191,223,255],
    "Green": [0,31,63,95,127,159,191,223,255],
    "Blue": [0,63,127,191, 255]
}

因此,对于9个红色值,9个绿色值和5个蓝色值,我得到405个颜色,这是错误的。我知道我需要8个红色和绿色值以及4个蓝色值,所以我只是稍微调整了一下:

255 / 8 7 = 36.57142857142857红色和绿色增量值

255 / 4 3 = 85表示蓝色增量值

所以这适用于蓝色,但现在我的红色和绿色增量值不是整数。

一旦我找到了映射,我就会像这样循环:

for(r in rgbData.get("Red")) {
    for(g in rgbData.get("Green")) {
        for(b in rgbData.get("Blue")) {
            colors.add("rgb ${r} ${g} ${b}")
        }
    }
}

这可能是一种完全不正确的方法来做我想做的事情,只是想表明我尝试了一些东西:)

更新

我尝试了@Marc B建议的方法,但似乎不对。例如,我生成的地图中没有白色(使用24位RGB是255, 255, 255)。使用他的方法这对我来说很有意义,因为可以看到最高的RGB值是224, 224, 192

全红== 111

111>> 5 == 11100000

全绿== 111

111>> 5 == 11100000

全蓝== 11

11>> 6 == 11000000

11100000 11100000 11000000 == 224,224,192

224,224,192 != 白色

以下是使用他的方法生成的地图:

{
    "Red": [0,32,64,96,128,160,196,224],
    "Green": [0,32,64,96,128,160,196,224],
    "Blue": [0,64,128,192]
}

它生成的调色板:

enter image description here

更新2:

在做了一些研究后,我意识到当“X颜色”(X是某些数字,如256,16777,216等)时,这些颜色几乎可以说是任何东西。没有预定义的256种颜色是“256”颜色,尽管有(如已经提到过的几种颜色)256种颜色的预定义组,对于特定实现而言是“256”颜色。我还能在我的组织维基上找到一个GIMP .gpl调色板文件,指定了我关注的256种颜色,所以我可以将值复制出来。

3 个答案:

答案 0 :(得分:2)

实际答案可能是肯定的。话虽如此,它确实是硬件依赖的东西。 @Marc B接近正确(可能对大多数人来说足够接近),但真正的答案取决于它取决于硬件,并且它不一定是从(硬件)实现到实现,但它可能足够精确到大多数人。

答案 1 :(得分:1)

转换的方法是将每个通道乘以您想要输出的最高级别,然后除以最高输入级别。

{
    "Red": [0,36,72,109,145,182,218,255],
    "Green": [0,36,72,109,145,182,218,255],
    "Blue": [0,85,170,255]
}

使用此方法,您不需要为每个通道提供偶数位,您可以为每个通道使用任意数量的级别。您可以获得更均匀的分布,但不能使用所有256种颜色。对于252种颜色,一种常见的排列是6/7/6:

{
    "Red": [0,51,102,153,204,255],
    "Green": [0,42,85,127,170,212,255],
    "Blue": [0,51,102,153,204,255]
}

答案 2 :(得分:1)

我知道这个答案可能有点晚了,但对其他人来说可能有用。 如果有人知道下面列出的算法是什么,请在评论中告诉我。

我目前正在使用不同的显示硬件,并且我遇到了将具有m位的通道转换为具有n位的通道的问题,其中m <1。 N;例如:将5位通道转换为8位通道。白色(b11111)应映射为白色(b11111111),黑色应映射为黑色。

例如,要将5位b10111映射到8位,我用原始数据中的MSB填充缺失的位:

b10111
 ^^^--- we need these three MSB again later, as 8-5 = 3 missing bits

左移3位:

b10111000

并使用MSB填充:

b10111101
      ^^^--- the MSBs

映射得非常好(您可能希望对不是全部1 s)的值进行舍入往返(您可以将少于8位转换为8位,转换回来,结果与原始值相同。)

如果较窄的通道宽度小于4位(如3),整个值将完全重复:

b101 -> b10110110