เปลี่ยนอัตราเฟรมเป็น ffmpeg โดยไม่ต้องเข้ารหัสใหม่


14

ฉันมีวิดีโอ mkv (h264) ที่ 23.976 fps (24000/1001) แต่ฉันต้องการแปลงเป็น 25fps โดยไม่ต้องเข้ารหัสซ้ำและลดคุณภาพ ฉันรู้ว่า mkvmerge สามารถทำได้ (ด้วยตัวเลือก - ค่าเริ่มต้น - ระยะเวลา '0: 25fps') แต่ฉันต้องการทำโดยตรงจาก ffmpeg ถ้าเป็นไปได้ตามเอกสารที่ควรใช้:

ffmpeg -i input.mkv -r 25 -vcodec copy output.mkv

แต่เมื่อฉันรันมันฉันจะได้วิดีโอ fps เดียวกันเท่านั้น วิธีการที่ถูกต้องที่จะทำ (ถ้ามี) ใน ffmpeg คืออะไร?


1
ฉันเชื่อว่าเป็นไปไม่ได้กับ FFmpeg ในขณะนี้ -rเข้ากันไม่ได้กับการคัดลอกกระแสและไม่มีตัวกรองบิตสตรีมเพื่อเปลี่ยนอัตราเฟรม
Ely

1
เลวร้ายเกินไป. ฉันจะต้องใช้ mkvmerge ทุกครั้ง ขอบคุณ
phate89

1
มีวิธีที่ซับซ้อนในการทำเช่นนี้กับ ffmpeg ปกติและวิธีโดยตรงในการทำเช่นนี้กับ ffmpeg รุ่น modded เก่า หากคุณสนใจฉันจะเขียนมันเป็นคำตอบ
Gyan

1
ใช่ขอบคุณ .. ฉันต้องการทำมันโดยไม่ต้องใช้เครื่องมือพิเศษ (ฉันต้องการ ffmpeg แล้ว)
phate89

1
@Mulvya คุณพูดถึงเรื่องนี้ใช่ไหม? ฉันลังเลที่จะเชื่อมโยงมัน แต่ตอนนี้เก่า .. สนใจวิธีที่ซับซ้อนในการทำกับ FFmpeg ปกติแม้ว่า
Ely

คำตอบ:


15

นี่คือวิธีการที่ใช้ FFmpeg เวอร์ชันปัจจุบัน มันขึ้นอยู่กับ demuxer ของ concat ที่ไม่ลดขนาด PTS ของอินพุตหลังจากไฟล์แรก แต่เพียงใช้อ็อฟเซ็ตคงที่ สมมติว่าคุณมีสตรีม 30 fps พร้อมไทม์สale 15360(ปกติของเอาต์พุต FFmpeg) กรอบซึ่งหมายความว่า0มี PTS 0และกรอบ30มี 15360PTS นี่จะกลายเป็นสตรีม 45 fps ถ้าเราสามารถเปลี่ยนไทม์เซลเป็น23040โดยไม่ส่งผลกระทบต่อค่า PTS

เป็นหลักนั่นคือสิ่งที่วิธีการด้านล่างทำ

1 . ระบุคุณสมบัติของแหล่งที่มา

Video: h264 (Main) (avc1 / 0x31637661), yuv420p, 1280x720 [SAR 1:1 DAR 16:9], 1171 kb/s,
       30 fps, 30 tbr, 15360 tbn (default)

tbnคุณต้องการที่จะทราบคุณสมบัติของแหล่งที่มาโดยเฉพาะอย่างยิ่งความละเอียดและ


2a (ไม่บังคับ) เปลี่ยนช่วงเวลาเป็นสิ่งที่สะดวกเพื่อให้การคำนวณง่ายขึ้น

ffmpeg -i in.mp4 -c copy -an -video_track_timescale 30 in-v30.mp4

สิ่งนี้ทำให้เรา

Video: h264 (Main) (avc1 / 0x31637661), yuv420p, 1280x720 [SAR 1:1 DAR 16:9], 1171 kb/s, \
       30 fps, 30 tbr, 30 tbn (default

ถ้าคุณทำตามขั้นตอนนี้ไทม์เซลใหม่ควรจะเท่ากันหรือเพิ่มตัวคูณของอัตราเฟรมดั้งเดิม

2b . คำนวณระยะเวลาที่จำเป็นเพื่อให้สำหรับ framerate เป้าหมายx, PTS ของกรอบ # ในแหล่งที่มาควรจะมีค่าเช่นเดียวกับใหม่x tbnหากคุณดำเนินการตามขั้นตอนที่ 2a นี่เป็นเรื่องง่ายมากและเป็นเพียงแค่เฟรมใหม่ ดังนั้นสำหรับเฟรมต่อวินาทีเป้าหมาย45ใหม่ที่ควรจะเป็นtbn45


3 . สร้างวิดีโอหลอกตา

ffmpeg -f lavfi -i color=s=1280x720:r=45:d=1 -profile:v main -video_track_timescale 45 0.mp4

คุณสมบัติทั้งหมดควรเหมือนกันเช่นความละเอียด, โปรไฟล์ H.264, รูปแบบพิกเซล, นับการตอบกลับ .. เป็นต้นเพื่อผลลัพธ์ที่ดีที่สุด


4 เชื่อมต่อวิดีโอ

ก่อนอื่นให้สร้างไฟล์ข้อความ

file '0.mp4'
file 'in-v30.mp4'

จากนั้นการตกลง

ffmpeg -f concat -i list.txt -c copy -video_track_timescale 45 45fps.mp4

ไฟล์ที่ส่งออกจะมีวิดีโอที่ 2 เล่นที่ 45 fps

5 . ทีนี้ลองตัด preroll จำลองออก

ffmpeg -ss 1.1 -i 45fps.mp4 -c copy -avoid_negative_ts make_zero in45.mp4

และคุณมี

Video: h264 (Main) (avc1 / 0x31637661), yuv420p, 1280x720 [SAR 1:1 DAR 16:9], 1757 kb/s, \
       45 fps, 45 tbr, 11520 tbn (default)

ฉันบอกว่าสิ่งนี้ถูกทำให้สับสน!


1
ฉลาดมากและคำตอบที่ดี
Rowe Morehouse
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.