视界原理之2D视频(二):视频文件里有什么

2D 视频文件里有什么

一个 MP4 文件不是"很多图片顺序塞在一起"。它更像一个带索引的媒体数据库:轨道、样本、时间戳、编码参数、同步点和显示元数据都被组织在里面。


先看文件内部结构

MP4 是容器,不是编码。H.264 / H.265 / AV1 负责压缩画面,MP4 / MOV / MKV 负责把压缩数据、时间信息和轨道关系组织起来。


1. 容器、轨道、样本三层要分清

层级 典型对象 工程含义
container MP4 / MOV / MKV 负责文件结构、索引、轨道组织
track video / audio / subtitle 每种媒体一条或多条轨道
sample / packet 一帧或一段编码数据 demuxer 读出来交给 decoder 的单位
codec bitstream NAL / OBU / slice decoder 真正解析的压缩语法

播放器打开文件时,先读容器,再选择轨道,再把 sample 转成 packet,最后 decoder 才开始理解 codec bitstream。


2. MP4 里哪些 box 最关键

不同容器细节不一样,但以 MP4 为例,工程上常见关键结构如下:

Box 作用 出问题的表现
ftyp 标识文件品牌和兼容性 兼容性判断失败
moov 元数据总入口 文件无法打开或索引缺失
mdat 真实媒体数据 packet 数据读取失败
trak 单条媒体轨道 找不到视频/音频轨
mdhd track 时间尺度和 duration 时长、同步异常
stsd sample description / codec config decoder 初始化失败
stts decoding time to sample DTS / duration 错误
ctts composition time offset B 帧 PTS 错误
stss sync sample / keyframe index seek 后花屏或失败
stsz sample size packet 边界错误
stco / co64 sample 文件偏移 读取错位、花屏

一个文件"ffprobe 看得到信息"不代表它的 sample table 一定完全正确。seek、变速、截断文件恢复这些场景会更容易暴露封装问题。


3. 编码参数到底保存在哪里

解码器启动前必须拿到 codec config。不同编码的名字不同,但作用相似。

编码 关键配置 用途
H.264 / AVC SPS、PPS、avcC 宽高、profile、level、参考帧、熵编码模式等
H.265 / HEVC VPS、SPS、PPS、hvcC 多层级、CTU、profile、tier、level 等
AV1 sequence header、av1C profile、level、bit depth、operating point 等
VP9 codec private / container fields profile、bit depth、color 等

参数集可以在码流里反复出现,也可以集中放在 extradata 里。移动端硬解尤其依赖初始化参数,如果 extradata 缺失、格式不对,可能表现为软解能播、硬解打不开。


4. 时间信息不只是 PTS

播放器同步靠时间信息,而不是靠"读到第几个 packet"。

时间字段 作用 常见坑
time scale / time base 把整数时间换成秒 单位换算错误导致快慢异常
DTS packet 应该进入 decoder 的时间顺序 B 帧场景必须单调
PTS frame 应该显示的时间 显示调度核心依据
duration sample 持续时间 VFR 视频必须逐帧看 duration
edit list 轨道起始偏移和裁剪 开头黑帧、音画偏移
start time 媒体流起点 多轨同步要统一基准

固定帧率视频可以看起来很简单;可变帧率、B 帧、edit list、音频 priming delay 混在一起时,时间线才是真正的复杂点。


5. 显示元数据决定"解出来以后怎么画"

decoder 主要关心码流语法,但 renderer 还需要显示相关信息。

信息 典型来源 显示阶段用途
rotation matrix container metadata 竖屏视频转正
clean aperture / crop container 或 codec 去掉编码填充边界
SAR / pixel aspect ratio codec VUI / container 计算 DAR,避免比例变形
color primaries VUI / container 判断 BT.709 / BT.2020 等色域
transfer characteristics VUI / HDR metadata 判断 SDR / PQ / HLG
matrix coefficients VUI 选择 YUV→RGB 矩阵
mastering display metadata HDR SEI / container HDR tone mapping
content light level HDR metadata 峰值亮度策略

很多"解码没错但看着不对"的问题,其实是显示元数据没有被正确传到渲染链路。


6. 解码时用什么,显示时用什么

信息 demuxer decoder renderer / display
track index 选择轨道 不关心 不关心
sample offset / size 读 packet 不关心 不关心
codec type 选择 decoder 初始化 decoder 可能用于能力策略
codec extradata 提取并传递 必须使用 通常不直接用
DTS 排 packet 决定输入顺序 间接影响队列
PTS 传递时间戳 输出 frame metadata 决定显示时刻
color metadata 传递 有时使用 必须使用
rotation / crop 传递 通常不用 必须使用
keyframe index seek flush / restart 间接影响首帧

这张表是排查播放器问题的分界线:先问"这个信息在哪一层被消费",再问"它有没有正确传过去"。


7. 文件异常怎么定位

现象 优先检查 典型工具方向
文件打不开 moov、track、codec config 容器解析、ffprobe
只有声音没画面 video track、decoder init codec id、extradata、profile
seek 后花屏 stss、IDR、参数集 keyframe index、packet 边界
时长不对 mdhd、duration、edit list time scale、start time
变速或卡顿 DTS / PTS / duration VFR、B 帧、time base
颜色异常 VUI、container color tags matrix、range、transfer
横竖屏错误 rotation matrix display matrix 传递链路

一句话总结

视频文件的价值不只是保存压缩码流,而是保存"decoder 如何解、renderer 如何画、播放器如何按时间组织"的全部上下文。

相关推荐
不会算法的笨小孩18 分钟前
异常的使用以及会出现的问题
开发语言·c++·c++11·异常
希和202720 分钟前
免费AI视频生成工具汇总(国内优先,适合做漫剧、短视频,Obsidian笔记版)
人工智能·笔记·音视频
且从容.34 分钟前
ubuntu安装flink
linux·ubuntu·flink
爱和冰阔落2 小时前
【Linux网络】TCP 服务器如何并发处理多个客户端?从 fork、僵尸进程到双重 fork
linux·运维·服务器·网络
程序员沉梦听雨2 小时前
WSL2的安装与使用
linux·wsl
微小的鱼2 小时前
Linux的渲染与显示系统链路
android·java·linux
Hhy_11072 小时前
《C++深度解构06》手撕 string —— 从底层内存管理到深浅拷贝彻底吃透
c语言·开发语言·c++·学习·visual studio
lisanmengmeng3 小时前
alertmanger 标签 rules 打上分组标签
linux·运维·服务器
青少儿编程课堂3 小时前
蓝桥杯青少组图形化省考报名倒计时·全国青少年信息素养大赛·电子学会图形化考级:校园黑白棋人机对战解析
c++·python·算法·bfs·信息学竞赛
严肃小白兔3 小时前
Cloudflare 更新 API Token 管理:从最小权限到自动化凭据安全
网络·安全·自动化