Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -45,14 +45,14 @@ private static string ComputeTransformArgs(ConversionPreset conversionPreset, He
if (conversionPreset.OutputType == OutputType.Mkv || conversionPreset.OutputType == OutputType.Mp4)
{
// This presets use h264 codec, the size of the video need to be divisible by 2.
switch (hwAccel)
{
case Helpers.HardwareAccelerationMode.CUDA:
scaleArgs = string.Format("scale_cuda=trunc(iw*{0}/2)*2:trunc(ih*{0}/2)*2:format=yuv420p", scaleFactor.ToString("#.##", CultureInfo.InvariantCulture));
break;
default:
scaleArgs = string.Format("scale=trunc(iw*{0}/2)*2:trunc(ih*{0}/2)*2", scaleFactor.ToString("#.##", CultureInfo.InvariantCulture));
break;
switch (hwAccel)
{
case Helpers.HardwareAccelerationMode.CUDA:
scaleArgs = string.Format("scale_cuda=trunc(iw*{0}/2)*2:trunc(ih*{0}/2)*2:format=yuv420p", scaleFactor.ToString("#.##", CultureInfo.InvariantCulture));
break;
default:
scaleArgs = string.Format("scale=trunc(iw*{0}/2)*2:trunc(ih*{0}/2)*2", scaleFactor.ToString("#.##", CultureInfo.InvariantCulture));
break;
}
}
else if (Math.Abs(scaleFactor - 1f) >= 0.005f)
Expand Down Expand Up @@ -104,10 +104,12 @@ private static string ComputeTransformArgs(ConversionPreset conversionPreset, He
transformArgs += rotationArgs;
}

if (hwAccel == Helpers.HardwareAccelerationMode.Off && (conversionPreset.OutputType == OutputType.Mkv || conversionPreset.OutputType == OutputType.Mp4))
if (hwAccel != Helpers.HardwareAccelerationMode.CUDA && (conversionPreset.OutputType == OutputType.Mkv || conversionPreset.OutputType == OutputType.Mp4))
{
// For H.264 in MP4/MKV, force yuv420p for broad player compatibility:
// http://trac.ffmpeg.org/wiki/Encode/H.264#Encodingfordumbplayers
// YUV planar color space with 4:2:0 chroma subsampling
// - Software encoding and non-CUDA hardware (e.g., AMF) come through this path.
// - CUDA is excluded here because the scale_cuda path above already sets format=yuv420p.
transformArgs += (transformArgs.Length > 0 ? "," : string.Empty) + "format=yuv420p";
//// TODO: maybe there should be an option for this on the settings?
}
Expand Down Expand Up @@ -324,7 +326,71 @@ private string H264EncodingSpeedToPreset(VideoEncodingSpeed encodingSpeed)
return "veryslow";
}

throw new Exception("Unknown H264 encoding speed.");
throw new ArgumentOutOfRangeException(nameof(encodingSpeed), encodingSpeed, "Unknown H264 encoding speed.");
}

/// <summary>
/// Convert video encoding speed to NVENC preset.
/// </summary>
/// <param name="encodingSpeed">The encoding speed.</param>
/// <returns>The NVENC preset.</returns>
private string H264EncodingSpeedToNVENCPreset(VideoEncodingSpeed encodingSpeed)
{
switch (encodingSpeed)
{
case VideoEncodingSpeed.UltraFast:
return "p1";

case VideoEncodingSpeed.SuperFast:
return "p2";

case VideoEncodingSpeed.VeryFast:
return "p3";

case VideoEncodingSpeed.Faster:
case VideoEncodingSpeed.Fast:
case VideoEncodingSpeed.Medium:
return "p4";

case VideoEncodingSpeed.Slow:
return "p5";

case VideoEncodingSpeed.Slower:
return "p6";

case VideoEncodingSpeed.VerySlow:
return "p7";
}

throw new ArgumentOutOfRangeException(nameof(encodingSpeed), encodingSpeed, "Unknown H264 encoding speed.");
}

/// <summary>
/// Convert video encoding speed to AMF quality mode.
/// </summary>
/// <param name="encodingSpeed">The encoding speed.</param>
/// <returns>The AMF quality mode.</returns>
private string H264EncodingSpeedToAMFQuality(VideoEncodingSpeed encodingSpeed)
{
switch (encodingSpeed)
{
case VideoEncodingSpeed.UltraFast:
case VideoEncodingSpeed.SuperFast:
case VideoEncodingSpeed.VeryFast:
case VideoEncodingSpeed.Faster:
case VideoEncodingSpeed.Fast:
return "speed";

case VideoEncodingSpeed.Medium:
case VideoEncodingSpeed.Slow:
return "balanced";

case VideoEncodingSpeed.Slower:
case VideoEncodingSpeed.VerySlow:
return "quality";
}

throw new ArgumentOutOfRangeException(nameof(encodingSpeed), encodingSpeed, "Unknown H264 encoding speed.");
}

/// <summary>
Expand Down
59 changes: 41 additions & 18 deletions Application/FileConverter/ConversionJobs/ConversionJob_FFMPEG.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,11 @@ namespace FileConverter.ConversionJobs
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.Text.RegularExpressions;
using CommunityToolkit.Mvvm.DependencyInjection;
using FileConverter.Controls;
using FileConverter.Services;
using System.Text.RegularExpressions;
using CommunityToolkit.Mvvm.DependencyInjection;
using FileConverter.Controls;
using FileConverter.Services;

public partial class ConversionJob_FFMPEG : ConversionJob
{
private readonly Regex durationRegex = new Regex(@"Duration:\s*([0-9][0-9]):([0-9][0-9]):([0-9][0-9])\.([0-9][0-9]),.*bitrate:\s*([0-9]+) kb\/s");
Expand Down Expand Up @@ -269,20 +269,43 @@ protected virtual void FillFFMpegArgumentsList()
audioArgs = $"-c:a aac -qscale:a {this.AACBitrateToQualityIndex(audioEncodingBitrate)}";
}

string videoCodec = "libx264";
string hwAccelArg = "";
if (hwAccel == Helpers.HardwareAccelerationMode.CUDA)
{
videoCodec = "h264_nvenc";
hwAccelArg = "-hwaccel cuda -hwaccel_output_format cuda";
}

string videoCodec = "libx264";
string videoCodecArgs = string.Format(
"-preset {0} -crf {1}",
this.H264EncodingSpeedToPreset(videoEncodingSpeed),
this.H264QualityToCRF(videoEncodingQuality));
string hwAccelArg = string.Empty;

switch (hwAccel)
{
case Helpers.HardwareAccelerationMode.CUDA:
videoCodec = "h264_nvenc";
int nvencQP = this.H264QualityToCRF(videoEncodingQuality);
videoCodecArgs = string.Format(
"-preset {0} -rc constqp -qp {1}",
this.H264EncodingSpeedToNVENCPreset(videoEncodingSpeed),
nvencQP);

hwAccelArg = "-hwaccel cuda -hwaccel_output_format cuda";
break;

case Helpers.HardwareAccelerationMode.AMF:
int amfQP = this.H264QualityToCRF(videoEncodingQuality);
int amfBFrameQP = Math.Min(51, amfQP + 2);
videoCodec = "h264_amf";
videoCodecArgs = string.Format(
"-usage transcoding -quality {0} -qp_i {1} -qp_p {1} -qp_b {2}",
this.H264EncodingSpeedToAMFQuality(videoEncodingSpeed),
amfQP,
amfBFrameQP);
break;
}

string encoderArgs = string.Format(
"-c:v {0} -preset {1} -crf {2} {3} {4}",
videoCodec,
this.H264EncodingSpeedToPreset(videoEncodingSpeed),
this.H264QualityToCRF(videoEncodingQuality),
audioArgs,
"-c:v {0} {1} {2} {3}",
videoCodec,
videoCodecArgs,
audioArgs,
videoFilteringArgs);

string arguments = string.Format("-n -stats {3} -i \"{0}\" {2} \"{1}\"", this.InputFilePath, this.OutputFilePath, encoderArgs, hwAccelArg);
Expand Down
15 changes: 8 additions & 7 deletions Application/FileConverter/Helpers.cs
Original file line number Diff line number Diff line change
Expand Up @@ -352,10 +352,11 @@ public static class InputCategoryNames
public const string Misc = "Misc";
}

public enum HardwareAccelerationMode
{
Off,
CUDA
}
}
}
public enum HardwareAccelerationMode
{
Off,
CUDA,
AMF
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,18 +10,20 @@ public class HardwareAccelerationModeToString : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
switch (value) {
case Helpers.HardwareAccelerationMode.Off:
return Properties.Resources.HardwareAccelerationModeOffName;
case Helpers.HardwareAccelerationMode.CUDA:
return Properties.Resources.HardwareAccelerationModeCUDAName;
switch (value) {
case Helpers.HardwareAccelerationMode.Off:
return Properties.Resources.HardwareAccelerationModeOffName;
case Helpers.HardwareAccelerationMode.CUDA:
return Properties.Resources.HardwareAccelerationModeCUDAName;
case Helpers.HardwareAccelerationMode.AMF:
return Properties.Resources.HardwareAccelerationModeAMFName;
}
return "Unknown";
return value?.ToString() ?? string.Empty;
}

public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
}
}
2 changes: 1 addition & 1 deletion Application/FileConverter/ViewModels/SettingsViewModel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ public class SettingsViewModel : ObservableRecipient, IDataErrorInfo

private ListCollectionView outputTypes;
private CultureInfo[] supportedCultures;
private Helpers.HardwareAccelerationMode[] hardwareAccelerationModes = { Helpers.HardwareAccelerationMode.Off, Helpers.HardwareAccelerationMode.CUDA };
private Helpers.HardwareAccelerationMode[] hardwareAccelerationModes = { Helpers.HardwareAccelerationMode.Off, Helpers.HardwareAccelerationMode.CUDA, Helpers.HardwareAccelerationMode.AMF };

public event Action OnPresetCreated;
public event Action OnFolderCreated;
Expand Down