web-dev-qa-db-fra.com

Comment utiliser l'encodage CRF avec nvenc dans ffmpeg?

Voici ma commande actuelle pour redimensionner des vidéos (1080p) de 2 Go à 300 Mo, mais cela prend beaucoup de temps:

mkdir newfiles  
for %%a in ("*.mp4") do ffmpeg -i "%%a" -c:v  libx264 -preset slow -crf 21 -c:a aac -b:a 128k -vf scale=678:-2 "newfiles\%%~na.mp4"  
pause

J'ai essayé nvenc avec mon NVIDIA GTX1070:

mkdir newfiles  
for %%a in ("*.mp4") do ffmpeg -i "%%a" -c:v h264_nvenc -preset slow -c:a aac -b:a 128k -vf scale=678:-2 "newfiles\%%~na.mp4"  
pause

La taille de sortie est toujours de 3⨉ ou 5⨉ la taille d'origine - nvenc n'utilise pas -crf.

Alors, comment utiliser nvenc avec ffmpeg pour convertir/redimensionner une vidéo de haute qualité et de petite taille? Devrais-je utiliser le GPU pour l'encodage?

14
hongducwb

Pour les codes basés sur CRF, transmettez les arguments suivants dans l'extrait ci-dessous à FFmpeg:

-c:v h264_nvenc -preset llhq -rc:v vbr_minqp -qmin:v 19 -qmax:v 21 -b:v 2500k -maxrate:v 5000k -profile:v high

Bien entendu, vous devrez vous adapter aux débits binaires cibles et définir une valeur -qp minimale et maximale cible. 19 est le paramètre recommandé, car visuellement identique à 0, tout en préservant un bon compromis sur la compression en fonction de la taille du fichier. 21 est la valeur de crête qui oblige le codeur à ne pas dépasser cette valeur dans la plage de débit spécifiée.

Notez que l'échelle -qp est logarithmique, ce qui signifie que 0 est essentiellement sans perte et que 51 serait le pire absolu.

La qualité peut être encore améliorée en ajoutant des options telles que B-frames (limitez-le à 4 au maximum, ce qui nécessite le profil principal H.264. Les profils de base ne prennent pas en charge les images B. Pour ce faire, transmettez -bf {uint} à l'encodeur vidéo, de sorte que -bf:v 4 entraîne l'utilisation de 4 images B par l'encodeur.

Les parties clés ici sont les arguments -preset et -rc:v vbr_minqp, qui vous permettent d’ajuster le codeur avec un débit prédéfini de variable et un débit maximum autorisé. (-b:v et -maxrate:v)

Et maintenant, petites notes sur NVENC et son réglage pour des encodages de haute qualité:

NVENC, comme tout autre encodeur basé sur du matériel, a plusieurs limitations, et en particulier avec HEVC, voici les limitations connues:

  1. Sur Pascal:

    Pour les codes HEVC, les limitations suivantes s'appliquent:

    • Les tailles CTU supérieures à 32 ne sont pas prises en charge.
    • Les images B en HEVC ne sont également pas prises en charge.
    • Les formats de texture pris en charge par l'encodeur NVENC limitent les espaces colorimétriques avec lesquels l'encodeur peut fonctionner. Pour l'instant, nous avons un support pour 4: 2: 0 (8 bits) et 4: 4: 4 (pour 10 bits). Les formats parasites tels que 4: 2: 2 10 bits ne sont pas pris en charge. Cela affectera certains flux de travail où de tels espaces de couleurs sont requis.
    • Regardez devant vous, le contrôle est également limité à 32 images. Vous voudrez peut-être consulter cet éditorial pour plus de détails.
  2. Et sur Maxwell Gen 2 (GPU série GM200x):

    Le codage HEVC manque des fonctionnalités suivantes:

L’impact ici pour Maxwell est que les scènes très chargées en mouvement avec HEVC avec des débits binaires limités peuvent souffrir d’un artefact (blocage) en raison de fonctions de recherche anormales manquantes et de capacités de filtrage de boucle adaptatives pour le décalage d’échantillon (SAO). Pascal a quelque peu amélioré cette fonctionnalité, mais selon la version du SDK avec laquelle l'encodeur vidéo a été créé, certaines fonctionnalités ne sont peut-être pas disponibles.

Par exemple, le mode de prédiction pondéré pour les codes H.264 sur Pascal nécessite NVENC SDK 8.0x et versions ultérieures, et ce mode de codage désactive également la prise en charge de la trame B. De même, la combinaison de scalers basés sur le matériel fonctionnant à partir des NPv (Nvidia Performance Primitives) avec NVENC peut apporter des améliorations de performances avec les applications de dimensionnement vidéo au détriment de la mise à l'échelle d'artefacts, en particulier avec du contenu redimensionné. Cela a également un impact sur le pipeline de codage vidéo puisque les fonctions de dimensionnement de NPP sont exécutées à partir des cœurs CUDA du GPU. L'impact sur les performances induit par la charge supplémentaire doit donc être analysé au cas par cas pour déterminer si les performances le compromis est acceptable.

Gardez cela à l'esprit: un encodeur matériel offrira toujours une personnalisation légèrement inférieure à une implémentation logicielle équivalente et, en tant que tel, votre kilométrage et la qualité de sortie acceptable seront toujours différents.

Et pour votre référence:

Avec FFmpeg, vous pouvez toujours vous référer aux paramètres d'un encodeur pour la personnalisation en:

ffmpeg -h encoder {encoder-name}

Ainsi, pour les encodeurs basés sur NVENC, vous pouvez exécuter:

ffmpeg -h encoder=hevc_nvenc

ffmpeg -h encoder=h264_nvenc

Vous pouvez également voir tous les encodeurs basés sur NVENC et les scalers basés sur NPP (s'ils sont construits tels quels) en exécutant:

for i in encoders decoders filters; do
    echo $i:; ffmpeg -hide_banner -${i} | egrep -i "npp|cuvid|nvenc|cuda"
done

Exemple de sortie sur mon banc d'essai:

encoders:
 V..... h264_nvenc           NVIDIA NVENC H.264 encoder (codec h264)
 V..... nvenc                NVIDIA NVENC H.264 encoder (codec h264)
 V..... nvenc_h264           NVIDIA NVENC H.264 encoder (codec h264)
 V..... nvenc_hevc           NVIDIA NVENC hevc encoder (codec hevc)
 V..... hevc_nvenc           NVIDIA NVENC hevc encoder (codec hevc)
decoders:
 V..... h263_cuvid           Nvidia CUVID H263 decoder (codec h263)
 V..... h264_cuvid           Nvidia CUVID H264 decoder (codec h264)
 V..... hevc_cuvid           Nvidia CUVID HEVC decoder (codec hevc)
 V..... mjpeg_cuvid          Nvidia CUVID MJPEG decoder (codec mjpeg)
 V..... mpeg1_cuvid          Nvidia CUVID MPEG1VIDEO decoder (codec mpeg1video)
 V..... mpeg2_cuvid          Nvidia CUVID MPEG2VIDEO decoder (codec mpeg2video)
 V..... mpeg4_cuvid          Nvidia CUVID MPEG4 decoder (codec mpeg4)
 V..... vc1_cuvid            Nvidia CUVID VC1 decoder (codec vc1)
 V..... vp8_cuvid            Nvidia CUVID VP8 decoder (codec vp8)
 V..... vp9_cuvid            Nvidia CUVID VP9 decoder (codec vp9)
filters:
 ... hwupload_cuda     V->V       Upload a system memory frame to a CUDA device.
 ... scale_npp         V->V       NVIDIA Performance Primitives video scaling and format conversion
19
林正浩

Je crois avoir trouvé une solution:

ffmpeg -hwaccel auto -i in.mp4 -c:v h264_nvenc -preset llhq -rc constqp -qp 21 -c:a copy out.mp4

Il semble que h264_nvenc utilise -qp au lieu de -crf. Cette option ne fonctionne que lorsque -rc est défini sur constqp.

4
Alexander01998

Pour -crf, le remplacement à partir de libx264 peut être -cq ou -qp à partir de h264_nvenc:

-crf Sélectionnez la qualité pour le mode de qualité constante

-cq Définir le niveau de qualité cible (0 à 51, 0 signifie automatique) pour le mode qualité constante dans le contrôle du débit VBR

-qp Méthode de contrôle du débit du paramètre de quantification constante (de -1 à 51) (par défaut -1)

La méthode d'encodage accéléré par le matériel la plus rapide:

ffmpeg -hwaccel cuvid -c:v h264_cuvid -resize 640x480 -i input.mp4 -c:v h264_nvenc -cq 21 -c:a copy output.mp4

-resize résolution sur l'entrée (en matériel); il n'est pas nécessaire que ffmpeg soit compilé avec --enable-libnpp pour le filtre scale_npp.

Pour plus d'informations:

ffmpeg -h encoder=h264_nvenc

ffmpeg -h denoder=h264_cuvid
3
abc