Change Video Frame Rate and Audio Speed in FFmpeg
Changing the frame rate of a video file while keeping the audio in perfect sync requires adjusting both the video’s presentation timestamps (PTS) and the playback speed of the audio track. This article provides a clear, step-by-step guide on how to use FFmpeg filters to speed up or slow down a video to a target frame rate while scaling the audio speed to match the new duration.
The Mathematical Principle
To change a video’s frame rate and adjust the audio accordingly, you must calculate a Speed Factor:
\[\text{Speed Factor} = \frac{\text{Target Frame Rate}}{\text{Original Frame Rate}}\]
- To speed up a video (e.g., playing a 24 fps video at 30 fps): The speed factor is greater than 1. Video presentation timestamps (PTS) must be compressed, and audio speed must be increased.
- To slow down a video (e.g., playing a 30 fps video at 24 fps): The speed factor is less than 1. Video presentation timestamps must be expanded, and audio speed must be decreased.
Scenario 1: Speeding Up Video and Audio (e.g., 24 fps to 30 fps)
In this scenario, we increase the speed of the video by a factor of 1.25 (\(30 / 24\)).
To make the video play 1.25 times faster, we multiply the video presentation timestamps (PTS) by \(0.8\) (\(1 / 1.25\)). We then set the audio tempo to \(1.25\).
Run the following FFmpeg command:
ffmpeg -i input.mp4 -filter_complex "[0:v]setpts=0.8*PTS[v];[0:a]atempo=1.25[a]" -map "[v]" -map "[a]" -r 30 output.mp4Command Breakdown:
-filter_complex: Allows us to process both video and audio streams simultaneously.[0:v]setpts=0.8*PTS[v]: Adjusts the video frames to appear 0.8 times faster.[0:a]atempo=1.25[a]: Speeds up the audio by 1.25x without changing the pitch.-map "[v]" -map "[a]": Maps the processed video and audio streams to the output.-r 30: Forces the output container to a constant frame rate of 30 fps.
Scenario 2: Slowing Down Video and Audio (e.g., 30 fps to 24 fps)
In this scenario, we decrease the speed of the video by a factor of 0.8 (\(24 / 30\)).
To make the video play slower, we multiply the video PTS by \(1.25\) (\(1 / 0.8\)). We then set the audio tempo to \(0.8\).
Run the following FFmpeg command:
ffmpeg -i input.mp4 -filter_complex "[0:v]setpts=1.25*PTS[v];[0:a]atempo=0.8[a]" -map "[v]" -map "[a]" -r 24 output.mp4Command Breakdown:
setpts=1.25*PTS: Delays the presentation timestamps, slowing down the video.atempo=0.8: Slows the audio down to 80% of its original speed.-r 24: Forces the output container to a constant frame rate of 24 fps.
Handling Extreme Speed Changes
The atempo filter in FFmpeg only supports values between
0.5 and 2.0. If you need to speed up or slow down a
video past these limits, you must chain multiple atempo
filters together.
For example, to speed up a video by a factor of 4 (e.g., changing 15 fps to 60 fps):
ffmpeg -i input.mp4 -filter_complex "[0:v]setpts=0.25*PTS[v];[0:a]atempo=2.0,atempo=2.0[a]" -map "[v]" -map "[a]" -r 60 output.mp4By multiplying \(2.0 \times 2.0\), you achieve the required \(4.0\text{x}\) audio speed adjustment to match the shortened video duration.