简单来说,视频编解码即是对构成图像的颜色进行处理,减少表达颜色效果所需要的比特数。
颜色效果是由颜色空间(colorspace)来表达,在视频编解码中常用的有两种: RGB和YUV。
1. RGB和YUV
RGB即三基色(红绿蓝),是日常生活中使用的一种表达方式。
三种基色的地位基本平等,在计算机里也基本由同样bit数来表达(当然也存在类似RGB565的)。
而YUV是根据人眼视觉系统的特性而定义的一种颜色空间。
其基本理论是:人眼对亮度信息比色度和饱和度更为敏感。
因而可以通过对亮度信息分配更多的bit并减少饱和度bit数,从整体上减少bit数而不减弱观看效果,起到压缩效果。
YUV常见的格式有: I420, YV12, NV12, NV21, 其像素排布如下
1 2 3 4
| I420: (1Y) + (1/4U) + (1/4V), | Y...Y | U..U | V..V | YV12: (1Y) + (1/4U) + (1/4V), | Y...Y | V..V | U..U | NV12: (1Y) + (1/4U) + (1/4V), | Y...Y | UVUV.. | NV21: (1Y) + (1/4U) + (1/4V), | Y...Y | VUVU.. |
|
2. YUV内存分布

3. YUV转换示例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
| # color convert void convert_nv21_to_i420(const char *src, char *dst, int stride, int height) { int ysize = stride * height; int usize = ysize / 4;
char *udst = dst + ysize; char *vdst = dst + ysize + usize;
const char *vusrc = src + ysize;
/* copy y color */ memcpy(dst, src, ysize);
/* copy u and v color */ for (int i=0; i < usize; i++) { udst[i] = vusrc[i*2+1]; vdst[i] = vusrc[i*2]; } }
|