如何解决FFmpeg添加水印时的视频XY轴适配问题?
Fixing FFmpeg Watermark Alignment & Adaptation Issues
Let's break down why your watermark isn't fitting correctly and fix it step by step.
First, let's look at your original command—there are a couple of potential issues here:
- Ambiguous variable references: Using
W/Handw/hworks in simple cases, but it's unclear which stream's dimensions you're targeting. Using explicit labels likemain_w/main_h(for your video) andoverlay_w/overlay_h(for your watermark) avoids confusion. - Parameter order: The
-presetflag is an encoder option, so it should come after your filter complex and before the output file path. - Unaccounted video rotation: Most mobile-recorded videos have rotation metadata (e.g., 90 degrees for portrait mode). FFmpeg doesn't auto-apply this rotation by default, so your
W/Hcalculations are using the raw video resolution, not the actual displayed resolution. - Missing encoder specification: Without explicitly setting
-c:v libx264, FFmpeg might fall back to a default encoder that doesn't play nicely with your filter setup.
Solution 1: Basic Centered Watermark (No Rotation Issues)
If your video doesn't have rotation metadata, fix the command order and use explicit variables:
String[] complexCommand = { "-i", AppUtils.videoPath, "-i", framelocalPath, "-filter_complex", "overlay=(main_w-overlay_w)/2:(main_h-overlay_h)/2", "-preset", "ultrafast", "-c:v", "libx264", dest1.getAbsolutePath() };
Solution 2: Handle Rotation + Scale Watermark to Fit Video
If your video has rotation (or you want the watermark to scale proportionally with the video), use this enhanced command:
String[] complexCommand = { "-i", AppUtils.videoPath, "-i", framelocalPath, "-filter_complex", // Auto-fix video rotation first to match displayed dimensions "[0:v]rotate=auto[main_video]; " + // Scale watermark to 20% of video height (adjust 0.2 to your needs), preserve aspect ratio "[1:v][main_video]scale2ref=w=oh*mdar:h=ih*0.2[scaled_watermark][main_video]; " + // Center the scaled watermark on the fixed video "[main_video][scaled_watermark]overlay=(main_w-overlay_w)/2:(main_h-overlay_h)/2", "-preset", "ultrafast", "-c:v", "libx264", dest1.getAbsolutePath() };
Key Explanations:
rotate=auto: Automatically applies the video's rotation metadata, so your width/height calculations match how the video is actually displayed.scale2ref=w=oh*mdar:h=ih*0.2: Scales the watermark to 20% of the video's height while preserving its original aspect ratio. Change0.2to adjust the size (e.g.,0.15for 15% height).- Explicit variable names (
main_w,overlay_w): Eliminates any ambiguity about which stream's dimensions you're referencing.
Quick Debug Steps:
- Check if your video has rotation metadata:
Run this command in your terminal:
If it returns a number likeffprobe -v error -show_entries stream_tags=rotate -of default=noprint_wrappers=1:nokey=1 /path/to/your/video.mp490or270, rotation is likely the main issue. - Verify your watermark's dimensions:
If the watermark is larger than the video, scaling it down (like in Solution 2) is essential.ffprobe -v error -show_entries stream=width,height -of default=noprint_wrappers=1:nokey=1 /path/to/your/watermark.png
内容的提问来源于stack exchange,提问作者Harsh Joshi




