YUV文件-y,u,v分量验证
通过程序采集yuv数据,并落1帧数据到文件中;
一、 此处记录下思路变化:
- 1、 第一步是了解YUV格式,为什么会比RGB节省空间;
- 2、 二则是按照YUV数据格式读取: 因为没有任何消息头尾的封装,所以只需要看YUV是什么格式,再按照字节读取分量即可;
- 3、 验证总结:
-
验证时,最好以图片进行验证,视频可能会出现未知问题
-
最开始以为黑白图片是只存储YUV的y分量,malloc 开辟的空间也为分辨率的大小,(注意不是总图片的大小),校验时通过ffmpeg无法成功打开;
-
报错: > packet size 204800 < expected frame_size 614400
-
后来想到:
生成图片或者视频时, 每一个像素都是有三分量构成,即使YUV422, YUV420等,也不是说无UV分量,而是共享,所以怎么可能存储图片的时候,把UV分量丢弃;
所以存储黑白照的时候,只需要将原始数据流的uv分量改为128即可;
-
二、 验证过程
此处只用一帧来进行测试说明
命令
- ffplay -f rawvideo -video_size 640*480 -pixel_format yuyv422 -i light.yuv
- vim -b light.yuv 以二进制打开yuv文件
在vim下,
:%!xxd 以16进制阅读yuv文件, 用于修改 yuv像素字节内容
:%!xxd -r , 恢复16进制到2进制文件, 用于让ffmpeg能够继续展示YUV文件
三、 yuv原始数据和图片
四、 vim修改数据和图片
vim修改完后,一定要恢复到2进制文件,否则无法使用ffmpeg打开
五、代码
点击查看代码
void imageDealYUV422(const struct SBufInfo *const localBuf)
{
//YUVYUV ; 2-48b-6B; (char *)
//YUYV ; 2-32b-4B;
int y_chunck_size = localBuf->length; // TODO: 当size 为 length 的 n分之一 时,以640*480打开yuv视频,会竖向出现相同视频n副
unsigned char *y_buf = (unsigned char *)malloc(y_chunck_size * sizeof(unsigned char *));
memset(y_buf, 0, y_chunck_size);
unsigned char *buf_ptr = y_buf;
int u_flag=0;
int v_flag=0;
for (int yIndex = 0; yIndex < localBuf->length;)
{
//获取原始数据亮度值
*buf_ptr = *((unsigned char *)(localBuf->start) + yIndex);
//用于修改u,v分量
if (yIndex % 2 != 0)
{
if(u_flag == 0){
*buf_ptr = 128;
v_flag = 0;
u_flag = 1;
}
else if (v_flag == 0)
{
*buf_ptr = 255;
v_flag = 1;
u_flag = 0;
}
}
yIndex += 1; // TODO: 当1为n时,以640*480打开yuv视频,会横向出现相同视频n副
buf_ptr += 1;
}
fwrite(y_buf, sizeof(unsigned char), y_chunck_size, lFile);
fflush(lFile);
free(y_buf);
y_buf=NULL;
}
六、.YUV文件颜色-测试分布
Y | U | V | 颜色 | 图像 |
---|---|---|---|---|
num | 0 | 0 | 浅绿色 | 有 |
0 | 128 | 128 | 黑色(无亮度) | 无 |
0 | 0 | 0 | 深绿色 | 无 |
0 | num | num | 绿色 | 无 |
0 | 128 | 0 | 深绿色 | 无 |
0 | 0 | 128 | 更深绿色 | 无 |
0 | 255 | 255 | 紫色 | 无 |
255 | 128 | 128 | 白色(最亮) | 无 |
255 | 0 | 0 | 亮绿色 | 无 |
255 | 0 | 128 | 亮黄色 | 无 |
255 | 128 | 0 | 亮蓝色 | 无 |
255 | 255 | 255 | 亮紫色 | 无 |
num | 128 | 128 | 黑白色 | 有 |
num | 0 | num | 浅黄绿色 | 有 |
num | 128 | num | 黑白色 | 有 |
num | num | 0 | 深黄绿色 | 有 |
num | num | 128 | 黑白色 | 有 |
目前还有一个问题未解决:
yuv视频流数据保存时,当存储到文件的缓冲区申请空间为总像素字节大小的n分之一时,ffmpeg读取的图像会上下分成n份;
如下:
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 在鹅厂做java开发是什么体验
· 百万级群聊的设计实践
· WPF到Web的无缝过渡:英雄联盟客户端的OpenSilver迁移实战
· 永远不要相信用户的输入:从 SQL 注入攻防看输入验证的重要性
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析