Почему аппаратное кодирование ffmpeg дает результат более низкого качества, чем программное кодирование?

Почему аппаратное кодирование ffmpeg дает результат более низкого качества, чем программное кодирование?

Я использовал эту команду для перекодирования видео,

ffmpeg -hwaccel vaapi -hwaccel_device /dev/dri/renderD128 -hwaccel_output_format vaapi -i input.mp4 -c:v h264_vaapi -b:v 1M -maxrate 1.5M output.mp4

Полученное видео имеет свойства,

Duration: 00:01:03.92, start: 0.000000, bitrate: 1292 kb/s Stream #0:0(und): Video: h264 (High) (avc1 / 0x31637661), yuv420p(tv, bt709), 1920x1080 [SAR 1:1 DAR 16:9], 1159 kb/s, 25 fps, 25 tbr, 12800 tbn, 50 tbc (default)

Снимок экрана выглядит такэтот

Затем я использовал эту команду, которая декодирует видео на аппаратном уровне, но кодирует видео на программном уровне,

ffmpeg -hwaccel vaapi -hwaccel_device /dev/dri/renderD128 -hwaccel_output_format vaapi -i input.mp4 -vf 'deinterlace_vaapi=rate=field:auto=1,hwdownload,format=nv12' -c:v libx264 -crf 30 -r 25 output.mp4

В результате получается видео о свойствах,

Duration: 00:01:00.89, start: 0.000000, bitrate: 932 kb/s Stream #0:0(und): Video: h264 (High) (avc1 / 0x31637661), yuv420p(tv, bt709), 1920x1080 [SAR 1:1 DAR 16:9], 798 kb/s, 25 fps, 25 tbr, 12800 tbn, 50 tbc (default)

Скриншот выглядит такэтот

Очевидно, что второе видео имеет более низкий битрейт, но более высокое качество. Я хотел бы знать, почему. Я также хотел бы знать, как достичь второго результата с помощью аппаратного кодирования.

решение1

Короткий ответ: Потому что всё всегда является компромиссом.

Более длинный ответ: ASIC-кодеки неизбежно гораздо менее гибкие и гораздо менее умные, чем программные кодеки. Они также в первую очередь предназначены для высокоскоростных/низкоэнергетических/постоянных приложений битрейта, таких как потоковая передача в реальном времени, где артефакты предпочтительнее пропущенных кадров.

решение2

Я не уверен, насколько близко вы подойдете к хорошему программному кодировщику, но если ваше оборудование его поддерживает, вы также можете попробовать hevc_vaapi, который должен быть более эффективным.

Но и с h264_vaapi вы не должны использовать, -b:v 1Mтак как это не даст вам хороших результатов, если только вы не укажете что-то вроде15М.

Попробуйте -qp 22(и позже скорректируйте значение) или, может быть, даже лучше:

-rc_mode CQP -global_quality 22(и скорректируйте значение позже).

Вы также можете попробовать добавить -compression_level 1то, что должно обеспечить лучшее качество при более низкой скорости.

Варианты описаны здесь:https://ffmpeg.org/ffmpeg-codecs.html#VAAPI-кодеры

Также может быть полезно, особенно если вы хотите попробовать hevc_vaapi: https://www.tauceti.blog/posts/linux-ffmpeg-amd-5700xt-hardware-video-encoding-hevc-h265-vaapi/

Связанный контент