I want to encode a video that will be compatible with videos created by my phone. That way I can mux the new video with the original without re-encoding the original video. I use FFmpeg with the libx264 encoder. The following are the MediaInfo specs of the original video created by my phone:
ID : 1
Format : AVC
Format/Info : Advanced Video Codec
Format profile : [email protected]
Format settings : 1 Ref Frames
Format settings, CABAC : No
Format settings, Reference frames : 1 frame
Format settings, GOP : M=1, N=30
Codec ID : avc1
Codec ID/Info : Advanced Video Coding
Duration : 52 s 369 ms
Bit rate : 10.0 Mb/s
Width : 1 280 pixels
Height : 720 pixels
Display aspect ratio : 16:9
Frame rate mode : Variable
Frame rate : 30.000 FPS
Minimum frame rate : 29.625 FPS
Maximum frame rate : 30.405 FPS
Standard : NTSC
Color space : YUV
Chroma subsampling : 4:2:0
Bit depth : 8 bits
Scan type : Progressive
Bits/(Pixel*Frame) : 0.362
Stream size : 62.4 MiB (98%)
Title : VideoHandle
Language : English
Encoded date : UTC 2020-10-27 19:43:55
Tagged date : UTC 2020-10-27 19:43:55
Color range : Limited
Color primaries : BT.709
Transfer characteristics : BT.709
transfer_characteristics_Original : BT.601
Matrix coefficients : BT.709
mdhd_Duration : 52369
Codec configuration box : avcC
So far, I have figured out the following, which I think has gotten me close:
ffmpeg -i in.mp4 -c:v libx264 -profile:v baseline -level:v 3.1 -refs 1 \
-vsync 2 -filter:v scale="-1:720",pad="1280:720:720/2+ow/2",format="yuv420p" \
-x264-params keyint="30":scenecut="0" -c:a copy out.mp4
I'm having trouble setting frame rate. It should be variable @ 30 fps. I found this question in regards to variable frame rate. But it has no answer. Setting -minrate
& -maxrate
does not help. The output is constant frame rate @ 30 FPS. Parameter examples follow.
Outputs constant rate @ 30 fps:-vsync 2 -r 30 -minrate 29.625 -maxrate 30.405
Outputs variable rate @ 29.970:-vsync 2 -r 30.405
I also believe that I should be using -crf
or -qp
, but am not sure of the correct value(s).
Edit:
The command shown above results in the following specs:
ID : 1
Format : AVC
Format/Info : Advanced Video Codec
Format profile : [email protected]
Format settings : 1 Ref Frames
Format settings, CABAC : No
Format settings, Reference frames : 1 frame
Format settings, GOP : M=1, N=30
Codec ID : avc1
Codec ID/Info : Advanced Video Coding
Duration : 8 s 700 ms
Duration_FirstFrame : 33 ms
Bit rate : 2 606 kb/s
Width : 1 280 pixels
Height : 720 pixels
Display aspect ratio : 16:9
Frame rate mode : Constant
Frame rate : 30.000 FPS
Color space : YUV
Chroma subsampling : 4:2:0
Bit depth : 8 bits
Scan type : Progressive
Bits/(Pixel*Frame) : 0.094
Stream size : 2.69 MiB (95%)
Title : VideoHandle
Writing library : x264 core 160
Encoding settings : cabac=0 / ref=1 / deblock=1:0:0 / analyse=0x1:0x111 / me=hex / subme=7 / psy=1 / psy_rd=1.00:0.00 / mixed_ref=0 / me_range=16 / chroma_me=1 / trellis=1 / 8x8dct=0 / cqm=0 / deadzone=21,11 / fast_pskip=1 / chroma_qp_offset=-2 / threads=6 / lookahead_threads=1 / sliced_threads=0 / nr=0 / decimate=1 / interlaced=0 / bluray_compat=0 / constrained_intra=0 / bframes=0 / weightp=0 / keyint=30 / keyint_min=3 / scenecut=0 / intra_refresh=0 / rc_lookahead=30 / rc=crf / mbtree=1 / crf=23.0 / qcomp=0.60 / qpmin=0 / qpmax=69 / qpstep=4 / ip_ratio=1.40 / aq=1:1.00
Language : English
Codec configuration box : avcC
Is there anything else shown here that isn't compatible with the original video?
Sources that helped me:
Edit (2020-11-6 23:40 UTC):
After reading Gyan's answer, I used the -video_track_timescale
parameter to set a tbn
value to match the original video. But the concatenated video still does not display correctly. Did I miss something that should be matching? I'm looking over the ffprobe
output now.
Original video:
$ ffprobe -hide_banner -i VID_20201027_124301.mp4
Input #0, mov,mp4,m4a,3gp,3g2,mj2, from 'VID_20201027_124301.mp4':
Metadata:
major_brand : mp42
minor_version : 0
compatible_brands: isommp42
creation_time : 2020-10-27T19:43:55.000000Z
location : +42.5418-122.5700/
location-eng : +42.5418-122.5700/
com.android.version: 7.1.2
Duration: 00:00:52.40, start: 0.000000, bitrate: 10187 kb/s
Stream #0:0(eng): Video: h264 (Baseline) (avc1 / 0x31637661), yuv420p(tv, bt709/bt709/smpte170m), 1280x720, 10002 kb/s, SAR 1:1 DAR 16:9, 30 fps, 30 tbr, 90k tbn, 180k tbc (default)
Metadata:
creation_time : 2020-10-27T19:43:55.000000Z
handler_name : VideoHandle
Stream #0:1(eng): Audio: aac (LC) (mp4a / 0x6134706D), 48000 Hz, stereo, fltp, 128 kb/s (default)
Metadata:
creation_time : 2020-10-27T19:43:55.000000Z
handler_name : SoundHandle
FFmpeg encoded video:
$ ffprobe -hide_banner -i VID_20201027_124914-encoded.mp4
Input #0, mov,mp4,m4a,3gp,3g2,mj2, from 'VID_20201027_124914-encoded.mp4':
Metadata:
major_brand : isom
minor_version : 512
compatible_brands: isomiso2avc1mp41
encoder : Lavf58.29.100
Duration: 00:00:08.70, start: 0.000000, bitrate: 2732 kb/s
Stream #0:0(eng): Video: h264 (Constrained Baseline) (avc1 / 0x31637661), yuv420p, 1280x720 [SAR 1:1 DAR 16:9], 2596 kb/s, 30 fps, 30 tbr, 90k tbn, 60 tbc (default)
Metadata:
handler_name : VideoHandle
Stream #0:1(eng): Audio: aac (LC) (mp4a / 0x6134706D), 48000 Hz, stereo, fltp, 128 kb/s (default)
Metadata:
handler_name : SoundHandle
Edit (2020-11-7 00:05 UTC):
Did some more testing & found that when I concatenate the video using FFmpeg, it works. But if I concatenate using a different muxer, like Avidemux or MKVToolNix, it does not. I think this question has been answered by Gyan, but I'm going to keep it open just a little longer to see if there is any input on why the video does not work with the other muxers as I prefer to use those.
Ultimate ffmpeg parameters used:
ffmpeg -i in.mp4 -c:v libx264 -profile:v baseline -level:v 3.1 \
-refs 1 -r 30 -video_track_timescale 90k \
-filter:v scale="-1:720",pad="1280:720:720/2+ow/2",format="yuv420p" \
-x264-params keyint="30":scenecut="0" -c:a copy out.mp4
the keyint & scenecut params of -x264-params & framerate aren't required
Edit:
Created question about concatenation not working with Avidemux & MKVToolNix here.