开启辅助访问
 找回密码
 立即注册

怎样用 rgb 三元组理解色相、亮度和饱和度?

linjia6680 回答数5 浏览数1137
Python的matplotlib.colors 采用三元组 (r, g, b) 来表示颜色,r,g,b 都在 [0, 1] 范围内,例如 (0.1, 0.2, 0.5) 。
不理解色相、亮度、饱和度的关系,怎样用这个元组来理解这三者的关系呢?
假如有一台颜色 (0.1, 0.2, 0.5) ,怎样变化算是增加色彩饱和度,怎样变化算是增加亮度?
使用道具 举报
| 来自黑龙江 用Deepseek满血版问问看
smile826 | 未知
一张图通过几何的角度展示色彩三要素。
首先我们有一根数轴,范围是0~255,是R、G、B的取值空间。R、G、B的取值对应红、绿、蓝三个小球的位置。我们用一个矩形把三个小球包起来,称为一根“色棒”。色棒有三种属性:红绿蓝三个小球的相对位置、色棒在数轴上的位置、色棒的长度,这三种属性分别对应了色调、亮度、饱和度三要素。

  • 色调对应红绿蓝三个小球在色棒中的相对位置。色棒在数轴上可以移动,可以等比例伸缩,但只要三个小球在色棒中的相对位置不变,那么色调不变。
而对于亮度和饱和度,Photoshop和Windows画图的定义略有不同。
Photoshop定义


  • 亮度对应色棒右端点在数轴上的位置。当色棒右端点位于0时亮度最小,位于255时亮度最大。
  • 饱和度对应色棒的长度。维持色棒右端点位置(亮度)不变将其等比例伸缩,当色棒长度为0时,饱和度最小,当色棒伸展到最大长度,即左端点触碰到数轴最左端时,饱和度最大。
Windows定义


  • 亮度对应色棒中点在数轴上的位置。当色棒中点位于0时亮度最小,位于255时亮度最大。注意由于三个小球的位置不能超出数轴两端,因此当亮度最小或最大时,色棒的长度被挤压为零。
  • 饱和度对应色棒的长度。维持色棒中点位置(亮度)不变将其等比例伸缩,当色棒长度为零时饱和度最小,当色棒伸展到其所能达到的最大长度时,即左端点或右端点触碰到数轴端点时,饱和度最大。
这样我们就把RGB三元组与色彩三要素建立了一个直观的几何联系。可以看到Photoshop对亮度和饱和度的定义更加简单明了,色棒右端点决定了亮度,左端点决定了饱和度。
用Deepseek满血版问问看
回复
使用道具 举报
amu226 | 来自北京
知友 @王赟 Maigo 的答案很棒,不过,说明的方式更接近数学语言,理解起来相对较难。
下面我用更加「通俗」的语言来解释 色相亮度 饱和度 ,作为一个补充。
打开 Windows 系统自带的画图软件,在上方的「工具」中选择「编辑颜色」,你就可以看到一个经典的色域图,如下图所示:


「画图」软件中的「编辑颜色」界面

通过这个图,我们就可以直观上理解色相、亮度、饱和度了,如下图所示。(需要注意的是,在画图中,色相、饱和度和亮度的范围都是 0~240)


色相、饱和度、亮度


  • 色相,简而言之,代表了一个颜色的 RGB 主色。其中,红色为 0°,绿色为 120°,蓝色为 240°。如下图所示:


色相(色调)


  • 饱和度,简而言之,代表着一种颜色的「纯度」。饱和度越高,其混浊的部分,也就是偏灰色的成分就越少。


  • 亮度,简而言之,代表的一种颜色与「白色」的距离。亮度越高,颜色越白,反之则越黑。

我们知道,通常来讲, RGB 的范围通常是 0~255,那么,我们应该怎样用 RGB 来描绘 色相、饱和度和亮度呢?
下面,我们以 RGB =(60,120,100)为例,算出这个颜色的 色相、饱和度和亮度吧。


RGB=(60,120,100)

A 色相

在「编辑颜色」界面的首行,从左到右滑动光标,我们会发现,RGB 是以下面的方式变动的:
(255,0,0)(红,0°)—> (255,255,0)(黄,60°)—>(0,255,0)(绿,120°)—>
(0,255,255)(青,180°)—>(0,0,255)(蓝,240°)—>(255,0,255)(品红,300°)
可见:0°、120°、240° 对应光的三原色(红、绿、蓝);
60°、180°、300° 对应颜料三原色(黄、青、品红)。
反映到 RGB 上,我们先找到一个主色,也就是 RGB 中最大的数值。
对于 RGB =(60,120,100):
数值最大的是 G,也就是绿色,所以色相是在 120° 附近。
由于 R=60,B=100,颜色更偏蓝一点,所以色相的范围在 120°~180° 之间。
易见:120° 对应的是 (60,120,60),180° 对应的是 (60,120,120)
于是容易计算:


* 如果将 160° 从 (0,360°)映射到 (0,240) 的范围内,那么色相大约是 107。
B 亮度

在讨论「饱和度」前,我们先讨论「亮度」。
上面所提到的 红、黄、绿、青、蓝、品红 六种颜色,它们的亮度都是 0.5,从它们的 RGB 中,我们能发现什么?显然: RGB 中的最大值都是 255,而最小值都是 0;
于是,可以猜到,亮度的定义也非常简洁:

其中 M 为 RGB 的理论最大值,一般为 255
对于 RGB =(60,120,100):

* 如果将 0.353 从(0,1)映射到(0,240),大约为 85。
C 饱和度

相对来说,饱和度的计算会比较复杂,我试图用更直观的方式解释它。
直观感受:RGB 中最大值和最小值越接近,饱和度越低,反之,饱和度越高。
另外,当我们在「编辑颜色」的顶行移动光标并且调节「亮度」时,会发现一个现象:
当饱和度为最高(240)时,RGB 总有一个为 255 或 0,反之亦然。并且,亮度大于 0.5 时,RGB 中必存在 255,亮度小于 0.5 时,RGB 中必存在 0。
于是,我们可以直观的感受到:「饱和度」公式中,分子应该是类似 max(R,G,B)-min(R,G,B) 之类的表达式,分母应该包括 max(R,G,B)+min(R,G,B) 以及 M。
由亮度的表达式可知,其为 0.5 时, max(R,G,B)+min(R,G,B) = M,为了让饱和度表达式分母的函数在亮度为 0.5 处出现拐点,表达式应该包含绝对值函数:
|max(R,G,B)+min(R,G,B) - M|
进一步地,数学直觉告诉我,分母的表达式就是:
M- |max(R,G,B)+min(R,G,B) - M|
于是:

对于 RGB=(60,120,100):

* 如果将 0.333 从(0,1)映射到(0,240),其值为 80。
综上所述,我们从直观上理解了 色相、亮度、和饱和度的含义,并且求得当 RGB =(60,120,100)时,我们算得:

  • 色相为 160°(107/240);
  • 亮度为 0.353(85/240);
  • 饱和度为 0.333(80/240)。
而画图的「编辑颜色」告诉我,我的计算结果是 正确 的。


RGB=(60,120,100)

【总结】

当我们已知 R、G、B 的值时,我们可以将其映射到 色相E、亮度L 和饱和度S。
根据之前的分析,其映射公式如下:

  • 色相 E (范围 [0°,360°))
分成 6 段讨论:
1) R≥G≥B 时,E =0°+60°·(G-B)/(R-B)
2) G≥R≥B 时, E =120°-60°·(R-B)/(G-B)
3) G≥B≥R 时, E =120°+60°·(B-R)/(G-R)
4) B≥G≥R 时, E =240°-60°·(G-R)/(B-R)
5) B≥R≥G 时, E =240°+60°·(R-G)/(B-G)
6) R≥B≥G 时, E =360°-60°·(B-G)/(R-G)

  • 亮度 L (范围 [0,1])


  • 饱和度 S (范围 [0,1])
回复
使用道具 举报
泉州生活网 | 来自北京
谢邀。三个数值一起增大是增加亮度;缩小方差则是降低饱和度。详细的:

不得不写在前面的名词定义纠纷问题:在本回答的撰写过程中,发现关于亮度和明度定义、翻译上的争议,整理结果如下:
首先亮度和明度两个概念,其中一个是解释了单一色彩的色彩含量,另一个解释了一个颜色中R、G、B三原色的平均值,可反应其与白色的接近程度。
“色含量”像是一个物体受光照,光越少看上去越黑,光越多就越接近它本来的颜色。“平均值”则像是一个物体自身在发光,光线少的时候仍然是越黑,但是光线多的时候,就越像是白色。
所以每个色相都具有“色含量”,最高时为此色相最鲜艳的颜色,最低时全部为黑色。而任何颜色“平均值”最高时为白色,最低时为黑色。

  • 在Wikipedia的词条“Brightness”中,Brightness是“平均值”,Lightness是“色含量”。
  • Wikipedia词条“HSL and HSV”中,Lightness是“平均值”,Value是“色含量”。
  • 在Photoshop英文版中,Brightness的实际效果是“色含量”,Lightness的实际效果是“平均值”。
  • 在Photoshop中文版中,“亮度”的实际效果是“色含量”,“明度”的实际效果是“平均值”。
  • 百度百科认可“Brightness”翻译为“明度”,把它解释为“平均值”;“Lightness”翻译为“亮度”,把它解释为“色含量”。
对于英文的释义,我觉得HSL+HSV颜色体系和Adobe都出错的概率比较小,所以词条“Brightness”的解释应该错了,正确为Brightness是“色含量”Lightness是“平均值”。而中文释义上,百度百科对应错了翻译,明度应为Lightness亮度应为Brightness。在下文中,我明度和亮度都将做解释。
<hr/>好啦,在看此回答前,需要回忆高中数学中的如下内容:

  • 三维直角坐标系(三维笛卡尔坐标系)
  • 立体几何中投影的概念
  • 极坐标系
  • 向量的加法
这是一个RGB颜色制式和HSL模型中的色彩的转换问题。其实网上有很多详尽的算法,但是我想在这里用高中数学的知识更加直观地去解释这一转换。
在RGB颜色制式中,三个颜色中的每个颜色都有一个数值来表示这个颜色的多少,这个数值取值一般是0到255,正好是二进制中的八位数可以表示的“量程”。当然在理论上,你想用0.0到1.0来表示,或者用0%到100%来表示都可以。举例,R=255,G=0,B=0,则代表红色数量最大,绿色和蓝色无,因此最终显示的颜色为纯红色。若R=0,G=0,B=0,则代表三种颜色数量都为0,最终合成为纯黑色。若R=255,G=255,B=255,则三个颜色都拉满,合成出来的是纯白色。
首先解释最好理解的明度(Lightness)
我们引入一个三维直角坐标系,三个坐标轴分别代表R、G、B的数量。由于此数值有限,所以取值范围会在立体空间里形成一个正方体。任何一个RGB颜色制式中的色彩取值,都会对应到这个立方体内的一点。


现在我们从原点(0,0,0)到对角的顶点(255,255,255)连出一条直线,也就是一条体对角线。这条对角线就可以说是一条明度轴了,原点最暗,另一端最亮。而任何一个颜色对应到的一点在这条体对角线上的“投影”,就是这个颜色的明度(Lightness)。靠近原点就越暗,靠近(255,255,255)就越亮。

然后我们需要再引入一个极坐标系,来解释饱和度(Saturation)色相(Hue)


当中渐变圆形只是指示色相用的,重点看立体的棍状链接的模型

极坐标系由角度轴和距离轴构成。把红蓝绿三个颜色分别置于角度轴的0°、120°、240°,此时色相就被角度轴来表示。从图中也可以看到,从0°到120°中间的区域就是橙色、黄色这些红色到绿色的过渡颜色,其他区域也是同理,每个色相都映射一个角度。而让原点的颜色为灰色,越往外颜色越鲜艳,则距离轴代表的就是饱和度
题主问的是RGB三原色怎么理解色相和饱和度,这里我们再借助向量。把R、G、B映射到角度轴,R、G、B的数值为距离轴,绘制三个向量。假设我们现在有一个颜色,R=100,G=150,B=200,那我们就在极坐标中,画一个坐标为(100,0°)的向量,一个坐标为(150,120°)的向量,一个坐标为(200,240°)的向量。
然后把这三个向量做向量的加法,最终会落在一个点上。这个点的角度轴数值就是此颜色的色相,而距离轴数值就是它的饱和度了。


蓝色箭头终点即为此色,色相210°,饱和度50%

不过,这个极坐标是一个二维坐标,不能表示RGB颜色制式中的所有颜色,只能解释色相和饱和度。如何使其表示所有颜色?我们需要再添加一个纵轴,变成了这样:


这里添加的这根纵轴就是亮度(Brightness)。而这个模型就是HSB模型/HSV模型。此外,还有个HSL模型,就是把Brightness轴替换成Lightness轴,替换后其顶层所有颜色都为白色。
顶层的纵坐标是255,白色是255,红色也一样是255,顶层大家的“光的量”Brightness都是最大值。底层的坐标是0,白色是0,红色也是0,所以说亮度是表示单个颜色的含量的。但是红色在上一个三维直角模型中,其投影并未到明度轴的顶点,其三数值平均值只有255/3=85,远不到最大值255,“与白色的相近程度”还明显差得很远。
图中,顶层是白色和最鲜艳的颜色,底层则清一色是黑色,想到了什么?没错,Photoshop的调色板。Photoshop的调色板也是基于HSV模型设计的,色相轴被独立出来在右侧,亮度和饱和度在二维坐标中供调制。

主要的回答部分就到此结束了。此外再提及一下色环模型。


色环模型虽然也是一个立体的极坐标,但是和上一个HSV模型并不一样。区别在于:
其一,纵轴使用的是明度(Lightness),不是亮度(Brightness)。
其二,这个色环模型中的色相轴,红、黄、蓝三色之间互相间隔120°。而上面提到用于向量计算的极坐标中,是红、绿、蓝三色之间互相间隔120°。红蓝黄是艺术配色上的三原色,关乎人类的视觉体感;而红绿蓝是光学上的三原色,关乎RGB印刷(虽然印刷上更多用CMYK)和显示器显示。

以上。希望对答主和其他读者有帮助。内容多为个人理解,如有错误请指出。
回复
使用道具 举报
小草44 | 来自吉林
HSL 空间是把 RGB 空间经过一个非线性变换得到的。在一个空间中改变一个参数,往往导致另一个空间中三个参数都改变,体现出「牵一发而动全身」的效果。


左为 RGB 空间,右为 HSL 空间

由 RGB 参数计算 HSL 参数的公式如下:


感性认识是这样的:
Hue 叫色相,表示了颜色在色环上的角度。纯红色位于 0 度,纯绿色位于 120 度,纯蓝色位于 240 度。具体计算时,角度主要由 RGB 中最大的那个决定,由次大的那个进行修正。
Lightness 叫亮度,具体计算公式是 RGB 中最大值与最小值的平均值。
Saturation 叫饱和度,表示的是 RGB 三个值的对比有多强烈。其算式中分子 C 是 RGB 中最大值与最小值的差值,但当 L 特别大或特别小的时候,C 的范围有限,为了把它归一化到 [0,1],又除了个与亮度有关的分母。
<hr/>具体到题主的例子:现在有一个颜色 (0.1, 0.2, 0.5),这是一个比较暗的、略偏绿的蓝色。所以它的色相会略小于 240 度(具体值是 225 度),亮度 L = (0.1 + 0.5) / 2 = 0.3,饱和度分子 C = 0.5 - 0.1 = 0.4,分母为 0.6,所以饱和度为 0.4 / 0.6 ≈ 0.67。
调整色相:由于亮度、饱和度都只与 RGB 中的最大、最小值相关,所以若要仅调整色相,就要调整绿色 G 的值。增大 G 的值会让色相更偏向绿色,即减小,G = B 时色相最小,为 180 度;反之,减小 G 则会让色相增大,G = R 时色相最大,为 240 度。
调整亮度:要调整亮度,主要靠调整值最大和最小的 B 和 R,但要注意保持色相和饱和度不变。当 L < 0.5 时,饱和度 S 的公式可以简化为 (M - m) / (M + m)。为了保持饱和度不变,B 和 R 要同比例增减,增时亮度增加,减时亮度降低。为了保持色相不变,G 也要同比例增减。
调整饱和度:同样,调整饱和度靠的也是 B 和 R。为了保持亮度不变,其中一个增加多少,另一个就要减小多少。增大 B、减小 R 可以让饱和度增加;减小 B、增大 R 可以让饱和度降低。为了保持色相不变,也要调整 G 使它与 B、R 的差值之比与原来相同。
上面的各种调整都要注意不能超过 0 <= R <= G <= B <= 1 的范围。一旦超过,调整方法也会改变。
<hr/>本答案内容主要参考维基百科页面 HSL and HSV,也推荐题主阅读一下。
需要注意的是,含有 H、S 两个参数的颜色空间有很多,但由于第三个参数的不同,S 的定义也会有不同。
回复
使用道具 举报
lockbaby | 来自上海
谢邀,首先说我不懂Python。。
但是你这个问题我倒是可以帮到你。
(该回答只针对程序员了解颜色,至于ps中的色相和亮度算法有时候是一个更复杂的特殊算法)

但是帮之前你要先去看看色彩的文章,我已经写好了:
PHOTOSHOP中的色彩理论-UI中国-专业用户体验设计平台

在photoshop中,8位通道色模型下,R、G、B三个通道分别是0-255,一共是256个档位。
而这个模型你把它理解为是RGB三个灯泡,每个灯泡从灭到最亮只有10档。
假如有一个颜色是(0.1, 0.2, 0.5),你可以理解为是红色开了最暗的1档,绿色开了2档,蓝色开了5档。
如果要只增加“亮度”,可以三个值全部乘除一个系数,比如变成(0.2、0.4、1)
如果要只增加或减少“饱和度”,“饱和度”最高意味着该颜色拥有该色相下最纯的色光。这句话是啥意思?也就是“增加饱和” = “减掉掺灰"。
在(0.1、0.2、0.5)这个颜色下,你可以理解为他是由两个颜色合成的,
其中一个颜色是一个灰色(0.1、0.1、0.1)和一个纯饱和色(0、0.1、0.4)
这时候所谓的”增加饱和度“操作,在算法上只需要把三个值减掉最小的那个就行了。


总结一下:
a、增加饱和度
一个颜色(0.1、0.2、0.5)增加饱和度到最饱和不掺灰状态,
算法是减去该颜色中的那个灰色,在这个颜色中灰色是(Rmin、Gmin、Bmin)
表现在(0.1、0.2、0.5)中,灰色是(0.1、0.1、0.1)
所以最后得到的纯饱和色是(0、0.1、0.4)

b、降低饱和度
一个颜色(0.1、0.2、0.5)降低饱和到最不饱和状态,
算法是取RGB中最高位通道色,将其他三个通道都替换成它,就变成了最灰的那个灰色。
在(0.1、0.2、0.5)中,降低到最不饱和,其颜色是(0.5、0.5、0.5)的灰色

我已经说成这样了你应该明白了吧?
回复
使用道具 举报
快速回复
您需要登录后才可以回帖 登录 | 立即注册

当贝投影