【发布时间】:2026-01-19 12:05:01
【问题描述】:
我正在尝试在 HSI 色彩空间中绘制一个色轮。我得到的色轮有非常宽的青色、黄色和洋红色,看起来很不对劲。我见过的所有其他色轮都有带最宽的红色、绿色和蓝色。
这就是恒指色轮的外观吗?还是我的数学错了?我已经尝试了所有我能找到的 HSI 到 RGB 的 sn-p,并在书中查找了这个等式。这个方程有很多变化,但是当我画我的圆圈时,它们都会导致相同的结果。我唯一不同的是在最后夹紧通道。我的 Intensity 到处都是 1.0,Hue 是像素的角度(旋转一点),Saturation 是到中心距离的大小。
这是我将 HSI 转换为 RGB(Objective-C)的杂乱代码:
float r;
float g;
float b;
S = S > 1.0f ? 1.0f : S;
I = I > 1.0f ? 1.0f : I;
H = H > 1.0f ? H - 1.0 : H;
H = H * M_PI * 2.0;
H = fmod(H, M_PI * 2.0);
if(S==0.0f){
r = I;
g = I;
b = I;
} else{
if((H>=0.0) && (H<2.0*M_PI/3.0)){
b = (1.0f-S)/3.0f;
r = (1.0f + S*cosf(H) / cosf(M_PI/3.0-H))/3.0f;
g = 1.0f-r-b;
} else if((H>=2.0*M_PI/3.0) && (H<4.0*M_PI/3.0)){
H = H - 2.0f*M_PI/3.0f;
r = (1.0f-S)/3.0f;
g = (1.0f+S*cosf(H)/cosf(M_PI/3.0 - H))/3.0f;
b = 1.0f-r-g;
} else if ((H>=4.0*M_PI/3.0) && (H<2.0*M_PI)){
H= H-4.0f*M_PI/3.0f;
g = (1.0f-S)/3.0f;
b = (1.0f+S*cosf(H)/cosf(M_PI/3.0-H))/3.0f;
r = 1.0f-b-g;
}
}
if(r<0.0f)
r=0.0f;
if(g<0.0f)
g=0.0f;
if(b<0.0f)
b=0.0f;
float R = 3.0f*I*r;
float G = 3.0f*I*g;
float B = 3.0f*I*b;
if(R>1.0f)
R=1.0f;
if(G>1.0f)
G=1.0f;
if(B>1.0f)
B=1.0f;
【问题讨论】:
-
你试过降低强度吗?我猜在强度最大的情况下,原色最大并被剪裁为 1。因此混合色主导了*。
-
@user3386109 关于当 I=1 时原色被洗掉的说法是正确的。 RGB 颜色 (1,0,0),这是您可以得到的最红的颜色,只能映射到 I=1/3。您可以改用 HSV 或 HSL 吗?这些色彩空间可能会带来更直观的用户界面。
-
顺便说一下,通过快速查看您的代码,我没有发现任何问题。我认为最重要的问题不是 I = 1.0 的所有 H 和 S 值都映射到有效的 (R, G, B) 三元组。我认为这就是函数末尾剪辑代码的原因。
标签: c color-space color-wheel