常见视频原始数据格式分析 — RGB

1. RGB 简介

1.1 RGB 色彩模式

RGB 色彩模式是工业界的一种颜色标准,是通过对红®、绿(G)、蓝(B)三个颜色通道的变化以及它们相互之间的叠加来得到各式各样的颜色的。

Red、Green、Blue 每一种颜色值的范围是 0~255,所以每一个颜色用 1 个字节 = 8 个 bit 便可完全在计算机内部表示出来。而 R、G、B 不同的组合几乎产生了所有的颜色,当然自然界中的颜色比这些要远远丰富很多,采用 R、G、 B 的方式,如果以 24 色深表示的话,在计算机中可表示的颜色数量有 2^8 * 2 ^8 * 2 ^8 = 16777216 种颜色,虽没有自然界丰富,但也足以表示这个世界了。

1.2 RGB 的应用

目前的显示器大都是采用了RGB颜色标准。

电脑屏幕上的所有颜色,都由这红色绿色蓝色三种色光按照不同的比例混合而成的。一组红色绿色蓝色就是一个最小的显示单位。屏幕上的任何一个颜色都可以由一组 RGB 值来记录和表达。

在电脑中,RGB 的所谓 “多少” 就是指亮度,并使用整数来表示。通常情况下,RGB 各有 256 级亮度,用数字 0~255 表示。

1.3 RGB 原理

RGB 是从颜色发光的原理来设计定的,通俗点说它的颜色混合方式就好像有红、绿、蓝三盏灯,当它们的光相互叠合的时候,色彩相混,而亮度却等于两者亮度之总和,越混合亮度越高,即加法混合。

有色光可被无色光冲淡并变亮。

加法混合的特点:越叠加越明亮。

红、绿、蓝三个颜色通道每种色各分为 255 阶亮度,在 0 时 “灯” 最弱是关掉的,而在 255 时 “灯” 最亮。当三色数值相同时为无色彩的灰度色,而三色都为 255 时为最亮的白色,都为 0 时为黑色。

2. RGB 格式

简单来讲,RGB 在计算机中的表示主要分为两大类,一种是索引形式,一种是像素形式。

(1) 索引
诸如 RGB1、RGB4、RGB8,分别表示每个像素用 1 个 bit,、4 个 bit、 8 个 bit 来表示,那么,这些 bit 存储的并非是实际的 R、G、B 值,而是对应点的像素在调色板的索引。

(2) 像素形式
诸如 RGB565、RGB555、 RGB24、RGB32、ARGB32 这些格式,存储的是每一个像素点的 R、G、B 值。比如 RGB24,分别用 8 个 bit 去表示 R、G、B。

2.1 RGB 索引格式

RGB 索引格式是比较老的格式,比较节省空间,在计算机发展的初期存储的成本还是很高的,但是表现的色彩很有限,而随着存储成本的不断降低,以及用户越来越高的视觉体验需求,这些格式也就基本被抛弃,不再被使用了,所以深入研究的意义也并不很大。只做简单介绍。

常用的 RGB 索引格式有:RGB1、GRB4、RGB8

关于调色板,可以简单理解为通过编号映射到颜色的一张二维表。如 01 索引,表示红色。采用索引格式的 RGB,红色的像素对应存储的值便是索引 01。

1) RGB1

每个像素用 1 个 bit 表示,可表示的颜色范围为双色,即最传统的黑和白。

1 个 bit 只能表示 0、1两种值。需要调色板,不过调色板只包含两种颜色。

2)RGB4:

每个像素用 4 个 bit 表示,4 个 bit 所能够表示的索引范围是 0-15 共 16 个。也就是可以表示 16 种颜色。即调色板中包含 16 种颜色。

3)RGB8

每个像素用 8 个 bit 表示。8 个 bit 所能够表示的索引范围是 0-255 ,共 256 个。也就是可以表示 256 种颜色。即调色板中包含 256 种颜色。

2.2 RGB 像素格式

比较常用的 RGB 像素格式包括:RGB565、RGB555、RGB24、RGB32、 ARGB32 等,不同的格式本质便是对于每一种单色的不同存储和表示方法。

下面每一种格式按照简介、存储示意图以及获取具体像素的方法来讲解

1) RGB565
a) 概述

RGB565 格式每一个像素用 16 个 bit 来表示,也就是 2 个字节, 1 个 WORD。

R、G、B 分别用 5、6、5 个 bit 来表示,格式也因此而得名。

b) 存储示意图

image

c) 获取具体像素值方法

根据 RGB565 的存储方式,即可得到获取 R、G、B 分量的值。现假设计算机中存储某一个像素点的变量为 color, 数据类型为 short. 那么则有:

R = color & 0xF800, (获取高字节的 5 个 bit)
G = color & 0x07E0, (获取中间 6 个 bit)
B = color & 0x001F, (获取低字节 5 个 bit)
2) RGB55
a) 概述

RGB55 格式每一个像素用 16 个 bit 来表示,也就是 2 个字节, 1 个 WORD。但是最高位不用,R、G、B 分别用 5 个 bit 来表示。

b) 存储示意图

image

c) 获取具体像素值方法

根据 RGB55 的存储方式,即可得到获取 R、G、B 分量的值。现假设计算机中存储某一个像素点的变量为 color, 数据类型为 short. 那么则有:

R = color & 0x7C00, (获取高字节的 5 个 bit)
G = color & 0x03E0, (获取中间 5 个 bit)
B = color & 0x001F, (获取低字节 5 个 bit)
3) RGB24(RGB888)
a) 概述

RGB24 格式每一个像素用 24 个 bit 来表示,也就是 3 个字节。R、G、B 分量分别用 8 个 bit 来表示。

RGB24 也常被叫做 RGB888。

b) 存储示意图

image

c) 获取具体像素值方法

根据 RGB24 的存储方式,即可得到获取 R、G、B 分量的值。现假设计算机中存储某一个像素点的变量为 color, 数据类型为 short. 那么则有:

R = color & 0x000000FF, 
G = color & 0x0000FF00,
B = color & 0x00FF0000,
4) RGB32
a) 概述

RGB32 格式每一个像素用 32 个 bit 来表示,也就是 4 个字节。R、G、B 分量分别用 8 个 bit 来表示,存储顺序为 B、G、R,最后 8 个字节保留。

b) 存储示意图

image

c) 获取具体像素值方法

根据 RGB32 的存储方式,即可得到获取 R、G、B 分量的值。现假设计算机中存储某一个像素点的变量为 color, 数据类型为 short. 那么则有:

R = color & 0x0000FF00
G = color & 0x00FF0000,
B = color & 0xFF000000,

3. 几种常用 RGB 格式处理例子

3.1 RGB565 转 RGB888 的实现

16 bit RGB565 -> 24 bit RGB888 的转换由于精度不同,故需要做量化补偿。

下面简单介绍下量化补偿的原理:

量化补偿的方法:
1. 将原数据填充至高位
2. 对于低位,用原始数据的低位进行补偿
3. 如果仍然有未填充的位,继续使用原始数据的低位进行循环补偿

例子: 16 bit RGB565 -> 24 bit RGB888 的转换
16 bit RGB656: R4 R3 R2 R1 R0 G5 G4 G3 G2 G1 G0 B4 B3 B2 B1 B0
24 bit RGB888: R4 R3 R2 R1 R0 0 0 0 G5 G4 G3 G2 G1 G0 0 0 B4 B3 B2 B1 B0 0 0 0
24 bit RGB888: R4 R3 R2 R1 R0 R2 R1 R0 G5 G4 G3 G2 G1 G0 G1 G0 B4 B3 B2 B1 B0 B2 B1 B0

其中,第三行的 24 bit RGB888 数据是经过量化补偿的数据,对低位做了量化补偿。

代码实现:

void rgb565_to_rgb888(unsigned char *image, unsigned char *image888) 
{
    unsigned char R, G, B;

    R = *(image + 1) & 0xF8; // 补齐成:RRRRR000
    G = (*(image + 1) << 5) | (*image & 0xe0 >> 3); // 补齐成:GGGGGG00
    B = *image << 3 ; // 补齐成: BBBBB000

    // 补偿
    *(image888) = B | ((B & 0x38) >> 3); 
    *(image888 + 1) = G | ((G & 0x0c) >> 2); 
    *(image888 + 2) = R | ((R & 0x38) >> 3); 
}

3.2 RGB888 转 RGB565 的实现

同上,如果是 RGB888-> RGB565,在精度上减少了,故需要做量化压缩

下面简单介绍下量化压缩的原理:

量化压缩的方法:
三个字取高位

例子: 24 bit RGB888 -> 16 bit RGB565 的转换
24 bit RGB888:R7 R6 R5 R4 R3 R2 R1 R0 G7 G6 G5 G4 G3 G2 G1 G0 B7 B6 B5 B4 B3 B2 B1 B0
16 bit RGB656: R7 R6 R5 R4 R3 G7 G6 G5 G4 G3 G2 B7 B6 B5 B4 B3
unsigned short rgb_24_to_565(unsigned short r, unsigned short g, unsigned short b)
{
    return ((r << 8) & 0xF800) | ((g << 3) & 0x07E0) | ((b >> 3) & 0x001f);
}

待添加…

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值