RGB与Lab颜色空间互相转换
RGB与Lab颜色空间互相转换
1.Lab颜色空间
同RGB颜色空间相比(见博客《光与色的故事--颜色空间浅析》),Lab是一种不常用的色彩空间。它是在1931年国际照明委员会(CIE)制定的颜色度量国际标准的基础上建立起来的。1976年,经修改后被正式命名为CIELab。它是一种设备无关的颜色系统,也是一种基于生理特征的颜色系统。这也就意味着,它是用数字化的方法来描述人的视觉感应。Lab颜色空间中的L分量用于表示像素的亮度,取值范围是[0,100],表示从纯黑到纯白;a表示从红色到绿色的范围,取值范围是[127,-128];b表示从黄色到蓝色的范围,取值范围是[127,-128]。下图所示为Lab颜色空间的图示;
需要提醒的是,Lab颜色空间比计算机显示器、打印机甚至比人类视觉的色域都要大,表示为 Lab 的位图比 RGB 或 CMYK 位图获得同样的精度要求更多的每像素数据。虽然我们在生活中使用RGB颜色空间更多一些,但也并非Lab颜色空间真的一无所有。例如,在 Adobe Photoshop图像处理软件中,TIFF格式文件中,PDF文档中,都可以见到Lab颜色空间的身影。而在计算机视觉中,尤其是颜色识别相关的算法设计中,rgb,hsv,lab颜色空间混用更是常用的方法。
两者的区别:
RGB的是由红色通道(R)、绿色通道(G)、蓝色通道(B)组成的,最亮的红色+最亮的绿色+最亮的蓝色=白色;最暗的红色+最暗的绿色+最暗的蓝色=黑色;而在最亮和最暗之间,相同明暗度的红色+相同明暗度的绿色+相同明暗度的蓝色=灰色。在RGB的任意一个通道内,白和黑表示这个颜色的明暗度。所以,有白色或者灰白色的地方,R、G、B三个通道都不可能是黑色的,因为必须要有R、G、B三个通道来构成这些颜色。
而LAB不一样,LAB中的明度通道(L)专门负责整张图的明暗度,简单的说就是整幅图的黑白版。a通道和b通道只负责颜色的多少。a通道表示从洋红色(通道里的白色)至深绿色(通道里的黑色)的范围;b表示从焦黄色(通道里的白色)至袅蓝色(通道里的黑色)的范围;a、b通道里的50%中性灰色表示没有颜色,所以越接近灰色说明颜色越少,而且a通道和b通道的颜色没有亮度。这就说明了为什么在a、b通道中红色T恤的轮廓是那么的清晰!因为红色是洋红色+焦黄色组成的。
总的来说:
1、适合RGB通道抠的图大部分LAB模式能完成,反之不成立。
2、任何单一色调背景下,用通道抠有明显颜色区别的部分,用LAB模式很快能完成
3、LAB模式下对明度(L)通道做任何操作(如锐化、模糊等)不会影响到色相。
2.RGB转Lab颜色空间
RGB颜色空间不能直接转换为Lab颜色空间,需要借助XYZ颜色空间,把RGB颜色空间转换到XYZ颜色空间,之后再把XYZ颜色空间转换到Lab颜色空间。
RGB与XYZ颜色空间有如下关系:
仔细观察式(1),其中 X = 0.412453 * R + 0.412453 *G+ 0.412453B ; 各系数相加之和为0.950456,非常接近于1,我们知道R/G/B的取值范围为[ 0,255 ],如果系数和等于1,则X的取值范围也必然在[ 0,255 ]之间,因此我们可以考虑等比修改各系数,使其之和等于1,这样就做到了XYZ和RGB在同等范围的映射。这也就是为什么代码里X,Y,Z会分别除以0.950456、1.0、1.088754。
RGB2Lab关键代码实现:
//RGB2Lab Lab2RGB
const float param_13 = 1.0f / 3.0f;
const float param_16116 = 16.0f / 116.0f;
const float Xn = 0.950456f;
const float Yn = 1.0f;
const float Zn = 1.088754f;float gamma(float x){return x>0.04045?powf((x+0.055f)/1.055f,2.4f):(x/12.92);}; void RGB2XYZ(T_U8 R, T_U8 G, T_U8 B, float *X, float *Y, float *Z) { float RR = gamma(R/255.0);float GG = gamma(G/255.0);float BB = gamma(B/255.0);*X = 0.4124564f * RR + 0.3575761f * GG + 0.1804375f * BB; *Y = 0.2126729f * RR + 0.7151522f * GG + 0.0721750f * BB; *Z = 0.0193339f * RR + 0.1191920f * GG + 0.9503041f * BB; } void XYZ2Lab(float X, float Y, float Z, float *L, float *a, float *b) { float fX, fY, fZ; X /= (Xn); Y /= (Yn); Z /= (Zn); if (Y > 0.008856f) fY = pow(Y, param_13); else fY = 7.787f * Y + param_16116; if (X > 0.008856f) fX = pow(X, param_13); else fX = 7.787f * X + param_16116; if (Z > 0.008856) fZ = pow(Z, param_13); else fZ = 7.787f * Z + param_16116; *L = 116.0f * fY - 16.0f;*L = *L > 0.0f ? *L : 0.0f; *a = 500.0f * (fX - fY); *b = 200.0f * (fY - fZ); } int RGB2Lab(IMAGE_TYPE *bmp_img,float *lab_img)
{DWORD width,height,index;WORD biBitCount;T_U8 *dst,*bmp,R,G,B;float X,Y,Z,L,a,b;T_U32 line_byte;T_U16 i,j;BITMAPFILEHEADER bf;BITMAPINFOHEADER bi;memset(&bf, 0, sizeof(bf));memset(&bi, 0, sizeof(bi));bmp = bmp_img;memcpy(&bf,bmp,14);memcpy(&bi,&bmp[14],40);height = bi.biHeight;width = bi.biWidth;biBitCount = bi.biBitCount;//每一个像素由24 bits表示,即RGB分量每一个分量用8 bits表示line_byte = WIDTHBYTES(width*bi.biBitCount);dst = bmp_img+BMPHEADSIZE;for (i = 0; i <height;i++){for (j = 0;j < width;j++){index = i*line_byte+3*j;B = dst[index];G = dst[index+1];R = dst[index+2];RGB2XYZ(R,G,B,&X,&Y,&Z);XYZ2Lab(X,Y,Z,&L,&a,&b);lab_img[index] = L;lab_img[index+1] = a;lab_img[index+2] = b;}}return 0;}
3.Lab转RGB颜色空间
Lab2RGB关键代码实现:
extern const float param_13;
extern const float param_16116;
extern const float Xn;
extern const float Yn;
extern const float Zn;float gamma_XYZ2RGB(float x){return x>0.0031308?(1.055f*powf(x,(1/2.4f))-0.055):(x*12.92);};void XYZ2RGB(float X, float Y, float Z, unsigned char*R, unsigned char*G, unsigned char*B) { float RR , GG, BB ;RR = 3.2404542f * X - 1.5371385f * Y - 0.4985314f * Z; GG = -0.9692660f * X + 1.8760108f * Y + 0.0415560f * Z; BB = 0.0556434f * X - 0.2040259f * Y + 1.0572252f * Z; RR = gamma_XYZ2RGB(RR);GG = gamma_XYZ2RGB(GG);BB = gamma_XYZ2RGB(BB);RR = CLIP255(RR*255.0+0.5);GG = CLIP255(GG*255.0+0.5);BB = CLIP255(BB*255.0+0.5);*R = (unsigned char)RR; *G = (unsigned char)GG; *B = (unsigned char)BB; } void Lab2XYZ(float L, float a, float b, float *X, float *Y, float *Z) { float fX, fY, fZ; fY = (L + 16.0f) / 116.0; fX = a / 500.0f + fY;fZ = fY - b / 200.0f; if(powf(fY,3.0)>0.008856)*Y =powf(fY,3.0);else*Y = (fY-param_16116)/7.787f;if (powf(fX,3) > 0.008856) *X = fX * fX * fX; else *X = (fX - param_16116) / 7.787f; if (powf(fZ,3.0) > 0.008856) *Z = fZ * fZ * fZ; else *Z = (fZ - param_16116) / 7.787f; (*X) *= (Xn); (*Y) *= (Yn); (*Z) *= (Zn); } int Lab2RGB(IMAGE_TYPE *bmp_img,float *lab_img)
{DWORD width,height,index;WORD biBitCount;T_U8 *bmp,R,G,B,*Lab2BMP;float X,Y,Z,L,a,b;T_U32 line_byte;T_U16 i,j;BITMAPFILEHEADER bf;BITMAPINFOHEADER bi;FILE *Lab2BMP_fp = fopen("Lab2BMP.bmp","wb");if(NULL == Lab2BMP_fp){printf("Can't open Lab2BMP.bmp\n");return -1;}memset(&bf, 0, sizeof(bf));memset(&bi, 0, sizeof(bi));bmp = bmp_img;memcpy(&bf,bmp,14);memcpy(&bi,&bmp[14],40);height = bi.biHeight;width = bi.biWidth;biBitCount = bi.biBitCount;//每一个像素由24 bits表示,即RGB分量每一个分量用8 bits表示line_byte = WIDTHBYTES(width*bi.biBitCount);fwrite(&bf,sizeof(BITMAPFILEHEADER),1,Lab2BMP_fp);fwrite(&bi,sizeof(BITMAPINFOHEADER),1,Lab2BMP_fp);Lab2BMP = (T_U8*)malloc(height*line_byte);if (Lab2BMP == NULL){printf("Can't malloc LabBMP image.\n");return 0;}memset(Lab2BMP,0,height*line_byte);for (i = 0; i <height;i++){for (j = 0;j < width;j++){index = i*line_byte+3*j;L = lab_img[index];a = lab_img[index+1];b = lab_img[index+2];Lab2XYZ(L,a,b,&X,&Y,&Z);XYZ2RGB(X,Y,Z,&R,&G,&B);Lab2BMP[index] = B;Lab2BMP[index+1] = G;Lab2BMP[index+2] = R;}}fwrite(Lab2BMP, line_byte*height, 1, Lab2BMP_fp);fclose(Lab2BMP_fp); free(Lab2BMP);return 0;}
4.结果实例
左侧图像是原始图像,右侧图像经过RGB->XYZ->LAB->XYZ->RGB的转换结果图。
以D65光源下24色卡为例,对比其计算出来的RGB Lab值大小。
按照上述公式,计算出来的Lab值与EasyRGB和Photoshop计算出来的值比较,与EasyRGB差值比较小。之所以有所差异,是lab计算中选取的参考白点Xn、Yn、Zn以及设备RGB转XYZ的矩阵略有差异。与Photoshop比较,主要差异在于a分量,其他两个分量已经比较接近了。
常见的参考白点在XYZ颜色空间的坐标为:
Observer | 2° (CIE 1931) | 10° (CIE 1964) | Note | ||||
Illuminant | X2 | Y2 | Z2 | X10 | Y10 | Z10 | |
A | 109.850 | 100.000 | 35.585 | 111.144 | 100.000 | 35.200 | Incandescent/tungsten |
B | 99.0927 | 100.000 | 85.313 | 99.178; | 100.000 | 84.3493 | Old direct sunlight at noon |
C | 98.074 | 100.000 | 118.232 | 97.285 | 100.000 | 116.145 | Old daylight |
D50 | 96.422 | 100.000 | 82.521 | 96.720 | 100.000 | 81.427 | ICC profile PCS |
D55 | 95.682 | 100.000 | 92.149 | 95.799 | 100.000 | 90.926 | Mid-morning daylight |
D65 | 95.047 | 100.000 | 108.883 | 94.811 | 100.000 | 107.304 | Daylight, sRGB, Adobe-RGB |
D75 | 94.972 | 100.000 | 122.638 | 94.416 | 100.000 | 120.641 | North sky daylight |
E | 100.000 | 100.000 | 100.000 | 100.000 | 100.000 | 100.000 | Equal energy |
F1 | 92.834 | 100.000 | 103.665 | 94.791 | 100.000 | 103.191 | Daylight Fluorescent |
F2 | 99.187 | 100.000 | 67.395 | 103.280 | 100.000 | 69.026 | Cool fluorescent |
F3 | 103.754 | 100.000 | 49.861 | 108.968 | 100.000 | 51.965 | White Fluorescent |
F4 | 109.147 | 100.000 | 38.813 | 114.961 | 100.000 | 40.963 | Warm White Fluorescent |
F5 | 90.872 | 100.000 | 98.723 | 93.369 | 100.000 | 98.636 | Daylight Fluorescent |
F6 | 97.309 | 100.000 | 60.191 | 102.148 | 100.000 | 62.074 | Lite White Fluorescent |
F7 | 95.044 | 100.000 | 108.755 | 95.792 | 100.000 | 107.687 | Daylight fluorescent, D65 simulator |
F8 | 96.413 | 100.000 | 82.333 | 97.115 | 100.000 | 81.135 | Sylvania F40, D50 simulator |
F9 | 100.365 | 100.000 | 67.868 | 102.116 | 100.000 | 67.826 | Cool White Fluorescent |
F10 | 96.174 | 100.000 | 81.712 | 99.001 | 100.000 | 83.134 | Ultralume 50, Philips TL85 |
F11 | 100.966 | 100.000 | 64.370 | 103.866 | 100.000 | 65.627 | Ultralume 40, Philips TL84 |
F12 | 108.046 | 100.000 | 39.228 | 111.428 | 100.000 | 40.353 | Ultralume 30, Philips TL83 |
D65光源下,常见的RGB转XYZ以及XYZ转RGB矩阵如下表所示:
RGB Working Space | Reference White | RGB to XYZ [M] | XYZ to RGB [M]-1 |
Adobe RGB (1998) | D65 |
|
|
AppleRGB | D65 |
|
|
Best RGB | D50 |
|
|
Beta RGB | D50 |
|
|
Bruce RGB | D65 |
|
|
CIE RGB | E |
|
|
ColorMatch RGB | D50 |
|
|
Don RGB 4 | D50 |
|
|
ECI RGB | D50 |
|
|
Ekta Space PS5 | D50 |
|
|
NTSC RGB | C |
|
|
PAL/SECAM RGB | D65 |
|
|
ProPhoto RGB | D50 |
|
|
SMPTE-C RGB | D65 |
|
|
sRGB | D65 |
|
|
Wide Gamut RGB | D50 |
|
|
D50光源下常见的RGB转XYZ以及XYZ转RGB矩阵为:
RGB Working Space | Reference White | RGB to XYZ [M] | XYZ to RGB [M]-1 |
Adobe RGB (1998) | D50 |
|
|
AppleRGB | D50 |
|
|
Bruce RGB | D50 |
|
|
CIE RGB | D50 |
|
|
NTSC RGB | D50 |
|
|
PAL/SECAM RGB | D50 |
|
|
SMPTE-C RGB | D50 |
|
|
sRGB | D50 |
|
|
参考资料:
http://www.cnblogs.com/Imageshop/archive/2013/02/02/2889897.html
http://blog.csdn.net/grafx/article/details/59482320
http://www.easyrgb.com/en/math.php
http://www.brucelindbloom.com/
RGB与Lab颜色空间互相转换相关推荐
- RGB与Lab颜色空间互相转换 持续更新中
RGB与Lab颜色空间互相转换 1.Lab颜色空间 同RGB颜色空间相比(见博客<光与色的故事–颜色空间浅析>),Lab是一种不常用的色彩空间.它是在1931年国际照明委员会(CIE)制定 ...
- Python实现RGB和Lab颜色空间互转
Python实现RGB和Lab颜色空间互转 https://github.com/rubund/debian-home-assistant/blob/1a3e8f7e4b9ddec60a4380e14 ...
- 颜色空间系列2: RGB和CIELAB颜色空间的转换及优化算法
颜色空间系列代码下载链接:http://files.cnblogs.com/Imageshop/ImageInfo.rar (同文章同步更新) 在几个常用的颜色空间中,LAB颜色空间是除了RGB外,最 ...
- RGB和YCbCr颜色空间的转换及优化算法
RGB和YCbCr颜色空间转换和优化 转载于颜色空间系列3: RGB和YCbCr颜色空间的转换及优化算法 在常用的几种颜色空间中,YCbCr颜色空间在学术论文中出现的频率是相当高的,常用于肤色检测等等 ...
- 基于matlab的RGB到YCbCr颜色空间的转换
在matlab中,图像处理工具箱会将彩色图像当做RGB图像或者索引图像来处理.除了这两种颜色空间外还有其他一些以RGB模型为基础的颜色空间,如常见的YCbCr.HSV.HSI颜色空间等.这里只讲图像从 ...
- Python实现RGB转Lab颜色空间,PS:和PhotoShop转换结果一样
由于工作要求,需要把rgb颜色转成Lab颜色空间.网上一搜一大把的代码,但是和PS一对比,基本上都不对. 下面这张图是OpenCV官方文档的计算方法. 用Python实现代码如下: from math ...
- 从RGB到Lab色彩空间的转换
最近一直在学习绘制RGB,HSV,Lab色彩空间的直方图,其中也涉及到互相转换的知识,这是网上看到的介绍的. ============================================= ...
- 【Pytorch】rgb转lab颜色空间转换
最近有需要,自己按照opencv实现的方式,自测! 个别tensor,numpy互转参考:https://oldpan.me/archives/pytorch-tensor-image-transfo ...
- RGB与YCbCr颜色空间的转换
YCbCr是YUV经过缩放和偏移的翻版,可以看做YUV的子集.主要用于优化彩色视频信号的传输,使其向后相容老式黑白电视.与RGB视频信号传输相比,它最大的优点在于只需占用极少的频宽(RGB要求三个独立 ...
最新文章
- linux-压缩与解压缩(gz,zip,tar,jar,war)
- 何时会调用拷贝构造函数
- python下载完以后是什么样子_python下载后怎么用
- Linux系统开机自动加载驱动module
- Opencv数据符号说明
- guns 最新开源框架企业版下载_国内比较火的5款Java微服务开源项目
- 关于sql的正则表达式
- 手机html图片自适应屏幕大小,手机端 图片自适应屏幕尺寸
- esxi安装系统ndows,ESXI 安装 Windows Server 2012过程
- eureka服务下架、服务续期及eureka源码分析
- 亲身经历从软通外包到华为OD,两者有什么区别?
- android语音到账,支付宝到账语音包
- 【Autosar 存储栈Memery Stack 3.存储读写流程的要求与时序】
- 三七互娱秋招web前端笔试题编程题(使用原生JS实现一个英雄类Hero, 可以按照以下方式调用正确输出)
- 摩尔定律、安迪-比尔定律、反摩尔定律
- linux的内网地址映射到公网地址
- Android Manifest内容解析
- 你的电脑是不是github访问一段时间又不能访问了?提示无法访问此网站。教你原理,这次学会就不用再百度
- 京东网络开放之路——数据中心光互联技术的思考与实践
- 愚弄了上万人,AI开始文化入侵了?道翰天琼认知智能机器人平台API接口大脑为您揭秘。
热门文章
- day199-2019-01-05-英语流利阅读-待学习
- ROS-学习资料参考
- 【每天听见吴晓波-2016-07-04】上海房价未来五年还会翻番
- AUTOSAR DiagnosticLogAndTrace(DLT)模块功能概述(一)----DLT基础概念、与SWC\DEM\DET的交互、VFB Trace
- 原声大碟 -《仙剑奇侠传三·电视原声带》[MP3]
- GPT-3: 最强的人工智能?
- 计算机技术应用广泛以下属于科学计算方面,2016年12月计算机二级MSoffice选择题习题...
- latex 数学符号-- 希腊字母、上下标、分数、运算符、箭头、标注、分隔符、省略号、空白间距
- 杰理之外挂 FLASH 使用方法与注意点【篇】
- Psychtoolbox刺激呈现方式