我想展示一些像这个例子这样的图像
填充颜色由数据库中的一个字段决定,颜色为十六进制(例如:ClassX -> 颜色:#66FFFF)。现在,我想用所选颜色在填充上方显示数据(如上图所示),但我需要知道颜色是深还是浅,所以我知道这些词应该是白色还是黑色。有办法吗?tks
您需要将十六进制代码分成 3 部分以获得单独的红色、绿色和蓝色强度。代码的每 2 位数字代表一个十六进制(base-16)表示法的值。我不会在这里详细介绍转换的细节,它们很容易查找。
获得各个颜色的强度后,您可以确定颜色的整体强度并选择相应的文本。
if (red*0.299 + green*0.587 + blue*0.114) > 186 use #000000 else use #ffffff
186的阈值是基于理论的,但可以根据口味进行调整。根据低于 150 的阈值的评论可能更适合您。
编辑: 上面的内容很简单,效果也不错,似乎在 StackOverflow 上得到了很好的接受。但是,以下评论之一表明它在某些情况下可能导致不遵守 W3C 指南。因此,我推导出一个修改后的表格,它总是根据指南选择最高的对比度。如果您 不需要 遵守 W3C 规则,那么我会坚持使用上面更简单的公式。
W3C 建议中给出的对比度公式是(L1 + 0.05) / (L2 + 0.05),其中L1是最亮颜色L2的亮度,是最暗颜色的亮度,范围为 0.0-1.0。黑色的亮度为 0.0,白色的亮度为 1.0,因此替换这些值可让您确定对比度最高的值。如果黑色的对比度大于白色的对比度,则使用黑色,否则使用白色。鉴于您正在测试的颜色的亮度,因为L测试变为:
(L1 + 0.05) / (L2 + 0.05)
L1
L2
L
if (L + 0.05) / (0.0 + 0.05) > (1.0 + 0.05) / (L + 0.05) use #000000 else use #ffffff
这在代数上简化为:
if L > sqrt(1.05 * 0.05) - 0.05
或大约:
if L > 0.179 use #000000 else use #ffffff
唯一剩下的就是计算L。该公式也在指南中给出,它看起来像是从 sRGB 到线性 RGB 的转换,然后是ITU-R 建议的 BT.709亮度。
for each c in r,g,b: c = c / 255.0 if c <= 0.03928 then c = c/12.92 else c = ((c+0.055)/1.055) ^ 2.4 L = 0.2126 * r + 0.7152 * g + 0.0722 * b
不应更改 0.179 的阈值,因为它与 W3C 指南相关联。如果您发现结果不符合您的喜好,请尝试上述更简单的公式。