给视频加水印、台标、时间码?彻底搞懂 ffmpeg 水印实战(含动态与防去除)
发布视频怕被搬运、想打上自己的台标、或者做监控回放要叠加时间码——这些都要"加水印"。ffmpeg 的水印能力很强:文字水印(drawtext)、图片水印(overlay)、甚至动态移动水印都不在话下。这篇文章从基础到进阶一次讲透,并提醒几个版权与观感上的注意点,以及"为什么加水印必须重编码"。
一、为什么加水印必须重编码
水印本质是"把像素叠加到每一帧画面里",所以视频流一定会被重新编码(无法 -c copy)。好消息是音频可以 -c:a copy 不动。理解这点能避免"为什么加个水印这么慢"的困惑——它在逐帧重算画面。
二、文字水印(drawtext)
最简单的台标/署名:
ffmpeg -i input.mp4 -vf "drawtext=text='VidDown':x=10:y=10:fontsize=24:fontcolor=white" -c:a copy out.mp4
x=10:y=10左上角(距左 10 距上 10);fontsize/fontcolor控制字号颜色;- 中文必须指定中文字体,否则乱码/方块:
fontfile=/path/NotoSansCJK.ttc。
带阴影提升可读性:
-vf "drawtext=text='VidDown':fontsize=24:fontcolor=white:borderw=2:bordercolor=black:x=10:y=10"
三、图片 Logo 水印(overlay)
用透明 PNG 做角标:
ffmpeg -i input.mp4 -i logo.png -filter_complex "overlay=W-w-10:10" -c:a copy out.mp4
overlay=W-w-10:10:右上角(W=视频宽,w=水印宽,10 是边距);- 右下:
overlay=W-w-10:H-h-10; logo.png最好是带透明通道的 PNG。
四、动态移动水印(防去除)
静态水印容易被裁掉,动态水印更难处理:
ffmpeg -i input.mp4 -i logo.png -filter_complex \
"overlay=x='if(gte(t,0),mod(t*80,W-w),-w)':y='if(gte(t,0),mod(t*40,H-h),-h)'" \
-c:a copy out.mp4
x/y 用表达式随时间变化,水印在画面上巡回移动(mod 取模实现循环)。
五、时间码水印(监控/取证常用)
实时叠加视频时间码或系统时间:
ffmpeg -i input.mp4 -vf "drawtext=text='%{pts\:hms}':x=10:y=H-th-10:fontsize=20:fontcolor=yellow" -c:a copy out.mp4
%{pts\:hms} 显示当前播放时间(时分秒)。要显示真实录制时间可用 localtime 函数:text='%{localtime:%Y-%m-%d %H:%M:%S}'。
六、透明度与阴影
让水印不那么刺眼:
# 半透明
ffmpeg -i input.mp4 -i logo.png -filter_complex \
"[1]format=rgba,colorchannelmixer=aa=0.5[wm];[0][wm]overlay=W-w-10:10" -c:a copy out.mp4
colorchannelmixer=aa=0.5 把透明度设为 0.5。配合 box=1:boxcolor=black@0.3 给文字加半透明底框。
七、批量加水印
for f in *.mp4; do
ffmpeg -i "$f" -i logo.png -filter_complex "overlay=W-w-10:10" -c:a copy "wm_$f"
done
八、水印方案对比
| 类型 | 命令 | 适用 |
|---|---|---|
| 文字 | drawtext | 台标/署名/时间码 |
| 图片 | overlay | Logo |
| 动态 | x/y 表达式 | 防去除 |
| 半透明 | colorchannelmixer=aa | 柔和观感 |
九、常见翻车现场
| 现象 | 根因 | 解法 |
|---|---|---|
| 中文水印乱码/方块 | 没指定中文字体 | 加 fontfile=中文字体路径 |
| 水印位置跑偏 | x/y 表达式算错 | 先用固定坐标调试 |
| 透明 PNG 变白底 | 没处理 alpha | 加 format=rgba |
| 输出没声音 | 漏 map 音频 | -c:a copy 且确认音频被 map |
| 处理极慢 | 重编码整段 | 水印必须重编码,无法 -c copy |
十、法律与观感注意
- 版权:给别人的视频加水印宣称是自己有侵权风险;给自己内容加署名通常没问题,但别遮挡他人水印;
- 观感:水印别太大太刺眼,半透明 + 角落放置最友好;
- 防去除的边界:动态水印只是提高成本,无法绝对防止,真正防护靠 DRM(见 DRM 专题)。
十一、常见问题
Q:加水印能不重编码吗? 不能,水印是像素级叠加,必须重编码视频流(音频可 copy)。
Q:怎么让人更难去掉水印? 动态移动 + 多位置 + 半透明,但无法绝对防止;核心是版权声明而非技术防去除。
Q:能加水印同时不改分辨率吗? 能,overlay 不影响分辨率,只改像素内容。
Q:能不能只给某几秒加水印? 能,用 enable='between(t,5,15)' 限定时间段。
十二、端到端实战:给一集教程加角标+时间码
要同时叠加右下角 Logo 和左上角时间码,用 filter_complex 串联:
ffmpeg -i input.mp4 -i logo.png -filter_complex \
"[0:v]drawtext=text='%{localtime\:%H\:%M\:%S}':x=10:y=10:fontsize=20:fontcolor=yellow[vt];\
[vt][1]overlay=W-w-10:H-h-10[out]" \
-map "[out]" -map 0:a -c:a copy out.mp4
注意 filter 链里先把时间码画到视频([vt]),再和 Logo overlay,顺序很重要。
十三、只在某时间段显示水印
比如头尾 10 秒打台标、中间去掉:
-vf "drawtext=text='VidDown':enable='lt(t,10)+gt(t, Duration-10)':x=10:y=10:fontsize=24:fontcolor=white"
enable 用表达式控制;Duration 可换成具体秒数。
十四、更多 FAQ
Q:水印太挡画面? 降低 fontsize/透明度,或移角落;动态水印可调慢移动速度。
Q:能不能加水印同时裁剪画面? 能,filter 链里加 crop 或 scale 一起做。
Q:水印被平台自动去掉? 部分平台会重新编码或检测水印,技术层面无法阻止;核心是版权声明。
Q:视频本身有硬字幕,加水印覆盖了? 调整水印位置避开字幕区(通常在底部),或先去字幕再加。
Q:处理 4K 视频加水印很慢? 水印必须重编码,4K 慢属正常;用硬件编码(h264_nvenc)可加速。
小结
水印三板斧:drawtext 文字、overlay 图片、x/y 表达式 做动态。中文务必指定字体,透明用 format=rgba,动态水印防去除。代价是必须重编码视频,无法 -c copy,音频可保留无损。