fix: use VP9 codec for webm recording output (#779)
* fix: use VP9 codec for webm recording output The recording command hardcoded libx264 (H.264) which is incompatible with the WebM container format. WebM only supports VP8/VP9/AV1 codecs, causing ffmpeg to fail when users specify a .webm output file. Select codec based on output file extension: libvpx-vp9 for .webm, libx264 for other formats. Fixes #778 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor: use CRF mode for VP9 webm encoding Switch from bitrate target (-b:v 2M) to constant quality mode (-crf 30), which is the standard approach for screen recording (used by Puppeteer and recommended by ffmpeg VP9 guide). CRF adapts bitrate to scene complexity for more consistent quality. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: add -b:v 0 for true constant quality VP9 encoding Without -b:v 0, libvpx-vp9 uses its default bitrate target alongside -crf, resulting in constrained quality mode instead of true constant quality mode. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: pad video dimensions to even numbers for h264 compatibility libx264 requires width and height to be divisible by 2, but CDP screencast can capture frames with odd dimensions (e.g. 1280x577). Add pad filter to ensure even dimensions for all codecs. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: hyunjinee <leehj0110@kakao.com> Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.6
hyunjinee
parent
67986adffc
commit
44ce24fb48
+11
-15
@@ -73,22 +73,18 @@ pub fn recording_stop(state: &mut RecordingState) -> Result<Value, String> {
|
||||
|
||||
let output = &state.output_path;
|
||||
|
||||
// Encode with ffmpeg
|
||||
let codec_args: &[&str] = if output.ends_with(".webm") {
|
||||
&["-c:v", "libvpx-vp9", "-crf", "30", "-b:v", "0"]
|
||||
} else {
|
||||
&["-c:v", "libx264", "-preset", "fast"]
|
||||
};
|
||||
|
||||
let result = Command::new("ffmpeg")
|
||||
.args([
|
||||
"-y",
|
||||
"-framerate",
|
||||
"30",
|
||||
"-i",
|
||||
&frame_pattern,
|
||||
"-c:v",
|
||||
"libx264",
|
||||
"-pix_fmt",
|
||||
"yuv420p",
|
||||
"-preset",
|
||||
"fast",
|
||||
output,
|
||||
])
|
||||
.args(["-y", "-framerate", "30", "-i", &frame_pattern])
|
||||
.args(["-vf", "pad=ceil(iw/2)*2:ceil(ih/2)*2"])
|
||||
.args(codec_args)
|
||||
.args(["-pix_fmt", "yuv420p"])
|
||||
.arg(output)
|
||||
.output();
|
||||
|
||||
let _ = std::fs::remove_dir_all(&state.temp_dir);
|
||||
|
||||
Reference in New Issue
Block a user