1. YUV色彩空间基础:从RGB到YUV的转换与高通平台数据排布
做ISP图像处理,YUV是绕不开的核心话题。我刚开始接触高通平台时,就被YUV的各种格式绕晕过——明明都是YUV,为什么有的能直接显示,有的却花屏?说白了,YUV不是一种格式,而是一族格式。理解它的底层逻辑,是后面做边缘增强、降噪、色彩校正的根基。
1.1 为什么ISP要用YUV,而不是RGB?
传感器出来的原始数据是Bayer格式,经过ISP前端的黑电平校正、去马赛克后,会先转到RGB域做白平衡和颜色校正。但到了YUV域,才是真正的“重头戏”。
原因很简单:人眼对亮度敏感,对色度不敏感。YUV把亮度和色度分开,我们就可以对Y通道做精细的边缘增强,对UV通道做压缩或降采样,而人眼几乎察觉不到画质损失。我在项目中遇到过一位刚入行的同事,非要在RGB域做锐化,结果彩色边缘出现大量振铃——这就是没理解YUV分离的好处。
3. YUV与RGB的转换原理
YUV和RGB的转换,本质上是一个线性变换。不同标准(BT.601、BT.709、BT.2020)的系数略有差异,但高通平台默认使用BT.601(标清)或BT.709(高清)。
我个人的习惯是:先把公式记死,再理解物理意义。下面给出BT.601标准的转换矩阵:
RGB → YUV(正向转换)
Y = 0.299 * R + 0.587 * G + 0.114 * B
U = -0.147 * R - 0.289 * G + 0.436 * B + 128
V = 0.615 * R - 0.515 * G - 0.100 * B + 128
YUV → RGB(反向转换)
R = Y + 1.140 * (V - 128)
G = Y - 0.394 * (U - 128) - 0.581 * (V - 128)
B = Y + 2.032 * (U - 128)
你可能会问:为什么U和V要加128?因为YUV数据通常用8位无符号数存储,Y的范围是[16, 235],UV的范围是[16, 240]。加128是为了把零值映射到中间值,避免负值无法存储。
1.3 YUV采样格式:4:4:4、4:2:2、4:2:0
这是YUV域最容易被搞混的地方。我见过不少工程师,代码写对了,但数据排布理解错了,结果图像全是马赛克。
采样格式的核心思想是:对色度通道进行降采样。人眼对色度的空间分辨率远低于亮度,所以我们可以“偷懒”——少存一些UV数据。
| 采样格式 | 每4个像素的Y样本数 | 每4个像素的U/V样本数 | 数据压缩比 | 典型应用 |
|---|---|---|---|---|
| 4:4:4 | 4 | 4(每个像素都有完整UV) | 无压缩 | 专业视频编辑、屏幕截图 |
| 4:2:2 | 4 | 2(每2个像素共享一组UV) | 33% | 广播级视频、HDMI传输 |
| 4:2:0 | 4 | 1(每4个像素共享一组UV) | 50% | 消费级视频、JPEG、H.264 |
1.4 高通平台YUV数据排布
高通平台最常用的YUV格式是NV12和NV21。两者都是4:2:0采样,区别在于UV的排列顺序。
NV12(YUV 4:2:0 平面+半平面)
数据排布如下:
- Y平面:连续存储所有像素的Y值,大小为 width × height
- UV半平面:交错存储U和V值,大小为 width × height / 2
具体到内存布局:
Y[0] Y[1] Y[2] Y[3] ... Y[W*H-1]
U[0] V[0] U[1] V[1] ... U[W/2*H/2-1] V[W/2*H/2-1]
NV21(与NV12相反)
UV半平面中,V在前,U在后:
Y[0] Y[1] Y[2] Y[3] ... Y[W*H-1]
V[0] U[0] V[1] U[1] ... V[W/2*H/2-1] U[W/2*H/2-1]
1.5 知识体系总览
下面这张图总结了本章的核心知识点,我建议你把它存下来,后面每章都会用到这些基础概念。
1.6 实战中的注意事项
最后,分享几个我在高通平台上踩过的坑:
- Stride对齐:Y平面的stride不一定等于width。高通平台要求stride对齐到32或64字节。读取数据时一定要用stride,而不是width。
- UV平面偏移:NV12的UV平面起始地址 = Y平面地址 + stride × height。但有些平台会在Y平面末尾填充额外的行(用于硬件加速),导致UV平面偏移。我建议用驱动返回的offset,不要自己算。
- 颜色空间转换:高通ISP输出的YUV是BT.601范围(Y:16-235, UV:16-240),但显示驱动可能期望全范围(0-255)。不做范围映射的话,图像会发灰或过曝。
嗯,YUV基础就讲到这里。这些概念看起来简单,但实际项目中80%的YUV相关问题都出在这些“基础”上。后面讲边缘增强时,你会频繁用到4:2:0的采样结构——因为边缘增强只在Y通道做,UV通道要保持原样,否则会出现彩色伪影。