计算最接近色盲友好的颜色?

Posted

技术标签:

【中文标题】计算最接近色盲友好的颜色?【英文标题】:Calculate the closest colourblind-friendly colour? 【发布时间】:2016-08-26 14:58:05 【问题描述】:

如何根据 #0a87af 等十六进制颜色代码或三个 RGB 值 (0-255) 计算最接近色盲友好的颜色。

我正在寻找一种有效的方法来计算或执行此操作,以便我可以在 php 或 Python 中实现它,并且该算法可用于为色盲人士提供更好的网站可访问性。

【问题讨论】:

首先,“色盲”不止一种。然后转换单一颜色是不好的,它总是至少取决于2(前景\背景) 您还应该问的一个问题是“什么是色盲友好的颜色?”任何单独的颜色都可以是色盲友好的,但如果你将该颜色与另一种发生冲突的颜色结合起来,它会突然变得不友好。在这里查看带有一些颜色的网格以及它们在不同版本的色盲中的外观:safecolours.rigdenage.com/colours2.html 所以我想应该添加第二个参数,背景颜色。色盲友好是否意味着“总是与背景相反的颜色”?我希望不是。感谢@NicRobertson,这是一个有用的列表。 嗯,你最好的选择可能是从该列表中选择在所有光谱中匹配良好的颜色,或者搜索一些对色盲友好的调色板。如果你有 Photoshop,你可以在你的设计上模拟色盲模式,这可以帮助你选择一个好的调色板。如果你需要动态生成主题,那会有点困难,但你可以尝试使用灰/白/黑来阻止自己生成一个视觉上非常糟糕的主题 【参考方案1】:

对于色盲用户来说,单一颜色不是问题(除非您想传达该色调的非常具体的含义);颜色之间的区别是。

给定两种或多种颜色,您可以使用colorsys 将它们转换为 HLS,并检查亮度差异是否足够。如果差异太小,请增加它,如下所示:

import colorsys
import re

def rgb2hex(r, g, b):
    return '#%02x%02x%02x' % (r, g, b)


def hex2rgb(hex_str):
    m = re.match(
        r'^\#?([0-9a-fA-F]2)([0-9a-fA-F]2)([0-9a-fA-F]2)$', hex_str)
    assert m
    return (int(m.group(1), 16), int(m.group(2), 16), int(m.group(3), 16))


def distinguish_hex(hex1, hex2, mindiff=50):
    """
    Make sure two colors (specified as hex codes) are sufficiently different.
    Returns the two colors (possibly changed). mindiff is the minimal
    difference in lightness.
    """

    rgb1 = hex2rgb(hex1)
    rgb2 = hex2rgb(hex2)

    hls1 = colorsys.rgb_to_hls(*rgb1)
    hls2 = colorsys.rgb_to_hls(*rgb2)

    l1 = hls1[1]
    l2 = hls2[1]

    if abs(l1 - l2) >= mindiff:  # ok already
        return (hex1, hex2)

    restdiff = abs(l1 - l2) - mindiff
    if l1 >= l2:
        l1 = min(255, l1 + restdiff / 2)
        l2 = max(0, l1 - mindiff)
        l1 = min(255, l2 + mindiff)
    else:
        l2 = min(255, l2 + restdiff / 2)
        l1 = max(0, l2 - mindiff)
        l2 = min(255, l1 + mindiff)

    hsl1 = (hls1[0], l1, hls1[2])
    hsl2 = (hls2[0], l2, hls2[2])

    rgb1 = colorsys.hls_to_rgb(*hsl1)
    rgb2 = colorsys.hls_to_rgb(*hsl2)

    return (rgb2hex(*rgb1), rgb2hex(*rgb2))


print(distinguish_hex('#ff0000', '#0000ff'))

【讨论】:

【参考方案2】:

正如其他人在他们的 cmets/answer 中提到的,两种颜色之间的对比很重要。

W3 已经创建了一种方法来定义颜色之间的最小对比度,以便通过不同级别的可访问性。

他们提供了描述 here 和计算它的公式在同一页面的底部,here:

contrast ratio = (L1 + 0.05) / (L2 + 0.05)

对于这个看似简单的公式,您需要使用您找到的另一个公式 here 计算两种颜色的相对亮度 L1L2

L = 0.2126 * R + 0.7152 * G + 0.0722 * B where R, G and B are defined as:

if RsRGB <= 0.03928 then R = RsRGB/12.92 else R = ((RsRGB+0.055)/1.055) ^ 2.4

if GsRGB <= 0.03928 then G = GsRGB/12.92 else G = ((GsRGB+0.055)/1.055) ^ 2.4

if BsRGB <= 0.03928 then B = BsRGB/12.92 else B = ((BsRGB+0.055)/1.055) ^ 2.4

而RsRGB、GsRGB、BsRGB定义为:

RsRGB = R8bit/255

GsRGB = G8bit/255

BsRGB = B8bit/255

文字和背景之间的最小对比度对于 AA 级应为 4.5:1,对于 AAA 级应为 7:1。这仍然为创造漂亮的设计留下了空间。

有implementation in JS by Lea Verou的例子。

这不会为您提供最接近您要求的颜色,因为在独特的背景上会有多个正面颜色提供相同的对比度结果,但这是计算对比度的标准方法。

【讨论】:

【参考方案3】:

Contrast-Finder 是一个开源在线工具(由 Open-S 和 M. Faure 编写),给定前景色和背景色,将根据 WCAG 计算对比度和对比度是否不足公式,将为您提供一堆具有足够对比度的背景或前景色,从而使用不同的算法提供选项(您必须告诉它是否要保持前景色或背景色,以及如果您希望对比度高于 4.5: 1 或 3:1 - AA 级 - 或 7:1 / 4.5:1 - AAA 级)。 它非常适合多种颜色。

来源 - 在 Java 中 - 在 GitHub 上。

注意:正如其他答案中已经写的那样,色盲的人(“有颜色缺陷的人”)只是关心颜色选择的人的一部分:视力不佳的人也是如此。当网页设计师在#FFF 上选择#AAA 时,对于许多人来说这是一个问题,而不会失去视力或色彩感知;他们只是在非最佳光照条件下有一个闪亮的 Retina® 屏幕......:p

【讨论】:

以上是关于计算最接近色盲友好的颜色?的主要内容,如果未能解决你的问题,请参考以下文章

R语言使用colorblinr包模拟色盲视觉将已有的ggplot2可视化结果图像使用edit_colors函数编辑转化为色盲视觉友好的可视化结果并自定设置色盲形式色盲严重级别

R语言使用colorblinr包模拟色盲视觉将已有的ggplot2可视化结果图像使用cvd_grid函数转化为色盲视觉友好的可视化结果显示多种视觉缺陷等级下的转化结果

R语言使用colorblinr包模拟色盲视觉将已有的ggplot2可视化结果图像使用cvd_grid函数转化为色盲视觉友好的可视化结果显示多种视觉缺陷等级下的转化结果

带有表格的边框颜色在电子邮件中是不是跨客户端友好?

生成 SEO 友好的 URL(slug)的最成熟的方式/lib 是啥?

高效且用户友好的方式来呈现加载缓慢的结果