mirror of
https://github.com/rosenbjerg/FFMpegCore.git
synced 2024-11-10 08:34:12 +01:00
Former-commit-id: f10c01e667
This commit is contained in:
commit
68c24621e9
33 changed files with 110 additions and 264 deletions
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Abstract class implements basic functionality of ffmpeg arguments
|
/// Abstract class implements basic functionality of ffmpeg arguments
|
||||||
|
|
|
@ -1,9 +1,6 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -2,7 +2,6 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.IO;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
@ -18,11 +17,6 @@ internal static string Speed(int cpu)
|
||||||
return $"-quality good -cpu-used {cpu} -deadline realtime ";
|
return $"-quality good -cpu-used {cpu} -deadline realtime ";
|
||||||
}
|
}
|
||||||
|
|
||||||
internal static string Audio(AudioCodec codec, AudioQuality bitrate)
|
|
||||||
{
|
|
||||||
return Audio(codec) + Audio(bitrate);
|
|
||||||
}
|
|
||||||
|
|
||||||
internal static string Audio(AudioCodec codec, int bitrate)
|
internal static string Audio(AudioCodec codec, int bitrate)
|
||||||
{
|
{
|
||||||
return Audio(codec) + Audio(bitrate);
|
return Audio(codec) + Audio(bitrate);
|
||||||
|
@ -69,11 +63,6 @@ internal static string Threads(int threads)
|
||||||
return $"-threads {threads} ";
|
return $"-threads {threads} ";
|
||||||
}
|
}
|
||||||
|
|
||||||
internal static string Input(Uri uri)
|
|
||||||
{
|
|
||||||
return Input(uri.AbsolutePath);
|
|
||||||
}
|
|
||||||
|
|
||||||
internal static string Disable(Channel type)
|
internal static string Disable(Channel type)
|
||||||
{
|
{
|
||||||
switch (type)
|
switch (type)
|
||||||
|
@ -87,21 +76,6 @@ internal static string Disable(Channel type)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
internal static string Input(VideoInfo input)
|
|
||||||
{
|
|
||||||
return $"-i \"{input.FullName}\" ";
|
|
||||||
}
|
|
||||||
|
|
||||||
internal static string Input(FileInfo input)
|
|
||||||
{
|
|
||||||
return $"-i \"{input.FullName}\" ";
|
|
||||||
}
|
|
||||||
|
|
||||||
internal static string Output(FileInfo output)
|
|
||||||
{
|
|
||||||
return $"\"{output.FullName}\"";
|
|
||||||
}
|
|
||||||
|
|
||||||
internal static string Output(string output)
|
internal static string Output(string output)
|
||||||
{
|
{
|
||||||
return $"\"{output}\"";
|
return $"\"{output}\"";
|
||||||
|
@ -122,11 +96,6 @@ internal static string Scale(int width, int height)
|
||||||
return $"-vf scale={width}:{height} ";
|
return $"-vf scale={width}:{height} ";
|
||||||
}
|
}
|
||||||
|
|
||||||
internal static string Scale(Size size)
|
|
||||||
{
|
|
||||||
return Scale(size.Width, size.Height);
|
|
||||||
}
|
|
||||||
|
|
||||||
internal static string Size(Size? size)
|
internal static string Size(Size? size)
|
||||||
{
|
{
|
||||||
if (!size.HasValue) return string.Empty;
|
if (!size.HasValue) return string.Empty;
|
||||||
|
|
|
@ -1,9 +1,4 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,9 +1,4 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,9 +1,5 @@
|
||||||
using System;
|
using System.Collections;
|
||||||
using System.Collections;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,9 +1,4 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents cpu speed parameter
|
/// Represents cpu speed parameter
|
||||||
|
|
|
@ -1,9 +1,4 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents frame output count parameter
|
/// Represents frame output count parameter
|
||||||
|
|
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents frame rate parameter
|
/// Represents frame rate parameter
|
||||||
|
|
|
@ -1,9 +1,6 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents loop parameter
|
/// Represents loop parameter
|
||||||
|
|
|
@ -1,9 +1,5 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents override parameter
|
/// Represents override parameter
|
||||||
|
|
|
@ -1,10 +1,5 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
@ -36,7 +31,7 @@ public ScaleArgument(VideoSize videosize)
|
||||||
/// <returns>String representation of the argument</returns>
|
/// <returns>String representation of the argument</returns>
|
||||||
public override string GetStringValue()
|
public override string GetStringValue()
|
||||||
{
|
{
|
||||||
return ArgumentStringifier.Scale(Value);
|
return ArgumentStringifier.Scale(Value.Width, Value.Height);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,8 +1,4 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents shortest parameter
|
/// Represents shortest parameter
|
||||||
|
|
|
@ -1,9 +1,4 @@
|
||||||
using System;
|
using System.Drawing;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Drawing;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
|
@ -17,7 +12,7 @@ public SizeArgument()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
public SizeArgument(Size? value) : base(value.HasValue ? value.Value : new Size())
|
public SizeArgument(Size? value) : base(value ?? new Size())
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,9 +1,4 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,10 +1,4 @@
|
||||||
using System;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents start number parameter
|
/// Represents start number parameter
|
||||||
|
|
|
@ -1,8 +1,4 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,9 +1,4 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
using FFMpegCore.FFMPEG.Enums;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,12 +1,4 @@
|
||||||
using FFMpegCore.FFMPEG.Enums;
|
namespace FFMpegCore.FFMPEG.Argument
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.IO;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG.Argument
|
|
||||||
{
|
{
|
||||||
public interface IArgumentBuilder
|
public interface IArgumentBuilder
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,8 +1,5 @@
|
||||||
using Newtonsoft.Json;
|
using System;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.IO;
|
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using RunProcessAsTask;
|
using RunProcessAsTask;
|
||||||
|
@ -86,4 +83,21 @@ protected async Task<string> RunProcessAsync(string filePath, string arguments)
|
||||||
return string.Join("", result.StandardOutput);
|
return string.Join("", result.StandardOutput);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static class ProcessHelpers
|
||||||
|
{
|
||||||
|
public static void RunProcess(string filePath, string arguments)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
public static async Task<string> RunProcessAsync(string fileName, string arguments)
|
||||||
|
{
|
||||||
|
var startInfo = new ProcessStartInfo(fileName, arguments);
|
||||||
|
startInfo.RedirectStandardOutput = true;
|
||||||
|
startInfo.RedirectStandardError = true;
|
||||||
|
|
||||||
|
var result = await ProcessEx.RunAsync(startInfo);
|
||||||
|
return string.Join("", result.StandardOutput);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -11,7 +11,6 @@
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using System.Text.RegularExpressions;
|
using System.Text.RegularExpressions;
|
||||||
|
|
||||||
|
@ -26,7 +25,7 @@ public class FFMpeg : FFBase
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Intializes the FFMPEG encoder.
|
/// Intializes the FFMPEG encoder.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public FFMpeg(): base()
|
public FFMpeg() : base()
|
||||||
{
|
{
|
||||||
FFMpegHelper.RootExceptionCheck(FFMpegOptions.Options.RootDirectory);
|
FFMpegHelper.RootExceptionCheck(FFMpegOptions.Options.RootDirectory);
|
||||||
|
|
||||||
|
@ -49,7 +48,8 @@ public FFMpeg(): base()
|
||||||
/// <param name="size">Thumbnail size. If width or height equal 0, the other will be computed automatically.</param>
|
/// <param name="size">Thumbnail size. If width or height equal 0, the other will be computed automatically.</param>
|
||||||
/// <param name="persistSnapshotOnFileSystem">By default, it deletes the created image on disk. If set to true, it won't delete the image</param>
|
/// <param name="persistSnapshotOnFileSystem">By default, it deletes the created image on disk. If set to true, it won't delete the image</param>
|
||||||
/// <returns>Bitmap with the requested snapshot.</returns>
|
/// <returns>Bitmap with the requested snapshot.</returns>
|
||||||
public Bitmap Snapshot(VideoInfo source, FileInfo output, Size? size = null, TimeSpan? captureTime = null, bool persistSnapshotOnFileSystem = false)
|
public Bitmap Snapshot(VideoInfo source, FileInfo output, Size? size = null, TimeSpan? captureTime = null,
|
||||||
|
bool persistSnapshotOnFileSystem = false)
|
||||||
{
|
{
|
||||||
if (captureTime == null)
|
if (captureTime == null)
|
||||||
captureTime = TimeSpan.FromSeconds(source.Duration.TotalSeconds / 3);
|
captureTime = TimeSpan.FromSeconds(source.Duration.TotalSeconds / 3);
|
||||||
|
@ -66,28 +66,28 @@ public Bitmap Snapshot(VideoInfo source, FileInfo output, Size? size = null, Tim
|
||||||
{
|
{
|
||||||
if (size.Value.Width == 0)
|
if (size.Value.Width == 0)
|
||||||
{
|
{
|
||||||
var ratio = source.Width / (double)size.Value.Width;
|
var ratio = source.Width / (double) size.Value.Width;
|
||||||
|
|
||||||
size = new Size((int)(source.Width * ratio), (int)(source.Height * ratio));
|
size = new Size((int) (source.Width * ratio), (int) (source.Height * ratio));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (size.Value.Height == 0)
|
if (size.Value.Height == 0)
|
||||||
{
|
{
|
||||||
var ratio = source.Height / (double)size.Value.Height;
|
var ratio = source.Height / (double) size.Value.Height;
|
||||||
|
|
||||||
size = new Size((int)(source.Width * ratio), (int)(source.Height * ratio));
|
size = new Size((int) (source.Width * ratio), (int) (source.Height * ratio));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
FFMpegHelper.ConversionExceptionCheck(source.ToFileInfo(), output);
|
FFMpegHelper.ConversionExceptionCheck(source.ToFileInfo(), output);
|
||||||
var container = new ArgumentContainer(
|
var container = new ArgumentContainer(
|
||||||
new InputArgument(source),
|
new InputArgument(source),
|
||||||
new VideoCodecArgument(VideoCodec.Png),
|
new VideoCodecArgument(VideoCodec.Png),
|
||||||
new FrameOutputCountArgument(1),
|
new FrameOutputCountArgument(1),
|
||||||
new SeekArgument(captureTime),
|
new SeekArgument(captureTime),
|
||||||
new SizeArgument(size),
|
new SizeArgument(size),
|
||||||
new OutputArgument(output)
|
new OutputArgument(output)
|
||||||
);
|
);
|
||||||
|
|
||||||
if (!RunProcess(container, output))
|
if (!RunProcess(container, output))
|
||||||
{
|
{
|
||||||
|
@ -97,7 +97,7 @@ public Bitmap Snapshot(VideoInfo source, FileInfo output, Size? size = null, Tim
|
||||||
output.Refresh();
|
output.Refresh();
|
||||||
|
|
||||||
Bitmap result;
|
Bitmap result;
|
||||||
using (var bmp = (Bitmap)Image.FromFile(output.FullName))
|
using (var bmp = (Bitmap) Image.FromFile(output.FullName))
|
||||||
{
|
{
|
||||||
using (var ms = new MemoryStream())
|
using (var ms = new MemoryStream())
|
||||||
{
|
{
|
||||||
|
@ -129,10 +129,8 @@ public VideoInfo Convert(
|
||||||
VideoInfo source,
|
VideoInfo source,
|
||||||
FileInfo output,
|
FileInfo output,
|
||||||
VideoType type = VideoType.Mp4,
|
VideoType type = VideoType.Mp4,
|
||||||
Speed speed =
|
Speed speed = Speed.SuperFast,
|
||||||
Speed.SuperFast,
|
VideoSize size = VideoSize.Original,
|
||||||
VideoSize size =
|
|
||||||
VideoSize.Original,
|
|
||||||
AudioQuality audioQuality = AudioQuality.Normal,
|
AudioQuality audioQuality = AudioQuality.Normal,
|
||||||
bool multithreaded = false)
|
bool multithreaded = false)
|
||||||
{
|
{
|
||||||
|
@ -142,13 +140,12 @@ public VideoInfo Convert(
|
||||||
|
|
||||||
_totalTime = source.Duration;
|
_totalTime = source.Duration;
|
||||||
|
|
||||||
var scale = VideoSize.Original == size ? 1 :
|
var scale = VideoSize.Original == size ? 1 : (double) source.Height / (int) size;
|
||||||
(double)source.Height / (int)size;
|
|
||||||
|
|
||||||
var outputSize = new Size(
|
var outputSize = new Size(
|
||||||
(int)(source.Width / scale),
|
(int) (source.Width / scale),
|
||||||
(int)(source.Height / scale)
|
(int) (source.Height / scale)
|
||||||
);
|
);
|
||||||
|
|
||||||
if (outputSize.Width % 2 != 0)
|
if (outputSize.Width % 2 != 0)
|
||||||
{
|
{
|
||||||
|
@ -194,7 +191,8 @@ public VideoInfo Convert(
|
||||||
|
|
||||||
if (!RunProcess(container, output))
|
if (!RunProcess(container, output))
|
||||||
{
|
{
|
||||||
throw new FFMpegException(FFMpegExceptionType.Conversion, $"The video could not be converted to {Enum.GetName(typeof(VideoType), type)}");
|
throw new FFMpegException(FFMpegExceptionType.Conversion,
|
||||||
|
$"The video could not be converted to {Enum.GetName(typeof(VideoType), type)}");
|
||||||
}
|
}
|
||||||
|
|
||||||
_totalTime = TimeSpan.MinValue;
|
_totalTime = TimeSpan.MinValue;
|
||||||
|
@ -226,7 +224,8 @@ public VideoInfo PosterWithAudio(FileInfo image, FileInfo audio, FileInfo output
|
||||||
|
|
||||||
if (!RunProcess(container, output))
|
if (!RunProcess(container, output))
|
||||||
{
|
{
|
||||||
throw new FFMpegException(FFMpegExceptionType.Operation, "An error occured while adding the audio file to the image.");
|
throw new FFMpegException(FFMpegExceptionType.Operation,
|
||||||
|
"An error occured while adding the audio file to the image.");
|
||||||
}
|
}
|
||||||
|
|
||||||
return new VideoInfo(output);
|
return new VideoInfo(output);
|
||||||
|
@ -248,10 +247,10 @@ public VideoInfo Join(FileInfo output, params VideoInfo[] videos)
|
||||||
FFMpegHelper.ConversionSizeExceptionCheck(video);
|
FFMpegHelper.ConversionSizeExceptionCheck(video);
|
||||||
var destinationPath = video.FullName.Replace(video.Extension, FileExtension.Ts);
|
var destinationPath = video.FullName.Replace(video.Extension, FileExtension.Ts);
|
||||||
Convert(
|
Convert(
|
||||||
video,
|
video,
|
||||||
new FileInfo(destinationPath),
|
new FileInfo(destinationPath),
|
||||||
VideoType.Ts
|
VideoType.Ts
|
||||||
);
|
);
|
||||||
return destinationPath;
|
return destinationPath;
|
||||||
}).ToList();
|
}).ToList();
|
||||||
|
|
||||||
|
@ -266,10 +265,11 @@ public VideoInfo Join(FileInfo output, params VideoInfo[] videos)
|
||||||
{
|
{
|
||||||
if (!RunProcess(container, output))
|
if (!RunProcess(container, output))
|
||||||
{
|
{
|
||||||
throw new FFMpegException(FFMpegExceptionType.Operation, "Could not join the provided video files.");
|
throw new FFMpegException(FFMpegExceptionType.Operation,
|
||||||
|
"Could not join the provided video files.");
|
||||||
}
|
}
|
||||||
return new VideoInfo(output);
|
|
||||||
|
|
||||||
|
return new VideoInfo(output);
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
|
@ -289,7 +289,8 @@ public VideoInfo JoinImageSequence(FileInfo output, double frameRate = 30, param
|
||||||
var temporaryImageFiles = images.Select((image, index) =>
|
var temporaryImageFiles = images.Select((image, index) =>
|
||||||
{
|
{
|
||||||
FFMpegHelper.ConversionSizeExceptionCheck(Image.FromFile(image.FullName));
|
FFMpegHelper.ConversionSizeExceptionCheck(Image.FromFile(image.FullName));
|
||||||
var destinationPath = image.FullName.Replace(image.Name, $"{index.ToString().PadLeft(9, '0')}{image.Extension}");
|
var destinationPath =
|
||||||
|
image.FullName.Replace(image.Name, $"{index.ToString().PadLeft(9, '0')}{image.Extension}");
|
||||||
File.Copy(image.FullName, destinationPath);
|
File.Copy(image.FullName, destinationPath);
|
||||||
|
|
||||||
return destinationPath;
|
return destinationPath;
|
||||||
|
@ -311,7 +312,8 @@ public VideoInfo JoinImageSequence(FileInfo output, double frameRate = 30, param
|
||||||
{
|
{
|
||||||
if (!RunProcess(container, output))
|
if (!RunProcess(container, output))
|
||||||
{
|
{
|
||||||
throw new FFMpegException(FFMpegExceptionType.Operation, "Could not join the provided image sequence.");
|
throw new FFMpegException(FFMpegExceptionType.Operation,
|
||||||
|
"Could not join the provided image sequence.");
|
||||||
}
|
}
|
||||||
|
|
||||||
return new VideoInfo(output);
|
return new VideoInfo(output);
|
||||||
|
@ -341,11 +343,13 @@ public VideoInfo SaveM3U8Stream(Uri uri, FileInfo output)
|
||||||
|
|
||||||
if (!RunProcess(container, output))
|
if (!RunProcess(container, output))
|
||||||
{
|
{
|
||||||
throw new FFMpegException(FFMpegExceptionType.Operation, $"Saving the ${uri.AbsoluteUri} stream failed.");
|
throw new FFMpegException(FFMpegExceptionType.Operation,
|
||||||
|
$"Saving the ${uri.AbsoluteUri} stream failed.");
|
||||||
}
|
}
|
||||||
|
|
||||||
return new VideoInfo(output);
|
return new VideoInfo(output);
|
||||||
}
|
}
|
||||||
|
|
||||||
throw new ArgumentException($"Uri: {uri.AbsoluteUri}, does not point to a valid http(s) stream.");
|
throw new ArgumentException($"Uri: {uri.AbsoluteUri}, does not point to a valid http(s) stream.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -395,7 +399,8 @@ public FileInfo ExtractAudio(VideoInfo source, FileInfo output)
|
||||||
|
|
||||||
if (!RunProcess(container, output))
|
if (!RunProcess(container, output))
|
||||||
{
|
{
|
||||||
throw new FFMpegException(FFMpegExceptionType.Operation, "Could not extract the audio from the requested video.");
|
throw new FFMpegException(FFMpegExceptionType.Operation,
|
||||||
|
"Could not extract the audio from the requested video.");
|
||||||
}
|
}
|
||||||
|
|
||||||
output.Refresh();
|
output.Refresh();
|
||||||
|
@ -436,8 +441,8 @@ public VideoInfo ReplaceAudio(VideoInfo source, FileInfo audio, FileInfo output,
|
||||||
|
|
||||||
public VideoInfo Convert(ArgumentContainer arguments)
|
public VideoInfo Convert(ArgumentContainer arguments)
|
||||||
{
|
{
|
||||||
var output = ((OutputArgument)arguments[typeof(OutputArgument)]).GetAsFileInfo();
|
var output = ((OutputArgument) arguments[typeof(OutputArgument)]).GetAsFileInfo();
|
||||||
var sources = ((InputArgument)arguments[typeof(InputArgument)]).GetAsVideoInfo();
|
var sources = ((InputArgument) arguments[typeof(InputArgument)]).GetAsVideoInfo();
|
||||||
|
|
||||||
// Sum duration of all sources
|
// Sum duration of all sources
|
||||||
_totalTime = TimeSpan.Zero;
|
_totalTime = TimeSpan.Zero;
|
||||||
|
@ -476,7 +481,7 @@ private bool RunProcess(ArgumentContainer container, FileInfo output)
|
||||||
{
|
{
|
||||||
var successState = true;
|
var successState = true;
|
||||||
|
|
||||||
CreateProcess(this.ArgumentBuilder.BuildArguments(container), _ffmpegPath, true, rStandardError: true);
|
CreateProcess(ArgumentBuilder.BuildArguments(container), _ffmpegPath, true, rStandardError: true);
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
@ -506,6 +511,7 @@ private bool RunProcess(ArgumentContainer container, FileInfo output)
|
||||||
throw new FFMpegException(FFMpegExceptionType.Process, _errorOutput);
|
throw new FFMpegException(FFMpegExceptionType.Process, _errorOutput);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return successState;
|
return successState;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -520,6 +526,7 @@ private void Cleanup(IEnumerable<string> pathList)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static Regex _progressRegex = new Regex(@"\w\w:\w\w:\w\w", RegexOptions.Compiled);
|
||||||
private void OutputData(object sender, DataReceivedEventArgs e)
|
private void OutputData(object sender, DataReceivedEventArgs e)
|
||||||
{
|
{
|
||||||
if (e.Data == null)
|
if (e.Data == null)
|
||||||
|
@ -532,14 +539,14 @@ private void OutputData(object sender, DataReceivedEventArgs e)
|
||||||
|
|
||||||
if (OnProgress == null || !IsWorking) return;
|
if (OnProgress == null || !IsWorking) return;
|
||||||
|
|
||||||
var r = new Regex(@"\w\w:\w\w:\w\w");
|
|
||||||
var m = r.Match(e.Data);
|
|
||||||
|
|
||||||
if (!e.Data.Contains("frame")) return;
|
if (!e.Data.Contains("frame")) return;
|
||||||
if (!m.Success) return;
|
|
||||||
|
|
||||||
var t = TimeSpan.Parse(m.Value, CultureInfo.InvariantCulture);
|
var match = _progressRegex.Match(e.Data);
|
||||||
var percentage = Math.Round(t.TotalSeconds / _totalTime.TotalSeconds * 100, 2);
|
if (!match.Success) return;
|
||||||
|
|
||||||
|
var processed = TimeSpan.Parse(match.Value, CultureInfo.InvariantCulture);
|
||||||
|
var percentage = Math.Round(processed.TotalSeconds / _totalTime.TotalSeconds * 100, 2);
|
||||||
OnProgress(percentage);
|
OnProgress(percentage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -8,8 +8,8 @@ namespace FFMpegCore.FFMPEG
|
||||||
{
|
{
|
||||||
public class FFMpegOptions
|
public class FFMpegOptions
|
||||||
{
|
{
|
||||||
private static string _ConfigFile = Path.Combine(".", "ffmpeg.config.json");
|
private static readonly string ConfigFile = Path.Combine(".", "ffmpeg.config.json");
|
||||||
private static string _DefaultRoot = Path.Combine(".", "FFMPEG", "bin");
|
private static readonly string DefaultRoot = Path.Combine(".", "FFMPEG", "bin");
|
||||||
|
|
||||||
public static FFMpegOptions Options { get; private set; } = new FFMpegOptions();
|
public static FFMpegOptions Options { get; private set; } = new FFMpegOptions();
|
||||||
|
|
||||||
|
@ -20,56 +20,37 @@ public static void Configure(FFMpegOptions options)
|
||||||
|
|
||||||
static FFMpegOptions()
|
static FFMpegOptions()
|
||||||
{
|
{
|
||||||
if (File.Exists(_ConfigFile))
|
if (File.Exists(ConfigFile))
|
||||||
{
|
{
|
||||||
Options = JsonConvert.DeserializeObject<FFMpegOptions>(File.ReadAllText(_ConfigFile));
|
Options = JsonConvert.DeserializeObject<FFMpegOptions>(File.ReadAllText(ConfigFile));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public string RootDirectory { get; set; } = _DefaultRoot;
|
public string RootDirectory { get; set; } = DefaultRoot;
|
||||||
|
|
||||||
public string FFmpegBinary
|
public string FFmpegBinary => FFBinary("FFMpeg");
|
||||||
|
|
||||||
|
public string FFProbeBinary => FFBinary("FFProbe");
|
||||||
|
|
||||||
|
private static string FFBinary(string name)
|
||||||
{
|
{
|
||||||
get
|
var ffName = name.ToLowerInvariant();
|
||||||
|
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
|
||||||
|
ffName += ".exe";
|
||||||
|
|
||||||
|
var target = Environment.Is64BitProcess ? "x64" : "x86";
|
||||||
|
if (Directory.Exists(Path.Combine(Options.RootDirectory, target)))
|
||||||
{
|
{
|
||||||
var target = Environment.Is64BitProcess ? "x64" : "x86";
|
ffName = Path.Combine(target, ffName);
|
||||||
var progName = RuntimeInformation.IsOSPlatform(OSPlatform.Windows) ? "ffmpeg.exe" : "ffmpeg";
|
|
||||||
|
|
||||||
if (Directory.Exists(Path.Combine(Options.RootDirectory, target)))
|
|
||||||
{
|
|
||||||
progName = Path.Combine(target, progName);
|
|
||||||
}
|
|
||||||
|
|
||||||
var path = Path.Combine(Options.RootDirectory, progName);
|
|
||||||
|
|
||||||
if (!File.Exists(path))
|
|
||||||
throw new FFMpegException(FFMpegExceptionType.Dependency,
|
|
||||||
$"FFMpeg cannot be found @ {path}");
|
|
||||||
|
|
||||||
return path;
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
public string FFProbeBinary
|
var path = Path.Combine(Options.RootDirectory, ffName);
|
||||||
{
|
|
||||||
get
|
|
||||||
{
|
|
||||||
var target = Environment.Is64BitProcess ? "x64" : "x86";
|
|
||||||
var progName = RuntimeInformation.IsOSPlatform(OSPlatform.Windows) ? "ffprobe.exe" : "ffprobe";
|
|
||||||
|
|
||||||
if (Directory.Exists(Path.Combine(Options.RootDirectory, target)))
|
if (!File.Exists(path))
|
||||||
{
|
throw new FFMpegException(FFMpegExceptionType.Dependency,
|
||||||
progName = Path.Combine(target, progName);
|
$"{name} cannot be found @ {path}");
|
||||||
}
|
|
||||||
|
|
||||||
var path = Path.Combine(Options.RootDirectory, progName);
|
return path;
|
||||||
|
|
||||||
if (!File.Exists(path))
|
|
||||||
throw new FFMpegException(FFMpegExceptionType.Dependency,
|
|
||||||
$"FFProbe cannot be found @ {path}");
|
|
||||||
|
|
||||||
return path;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,10 +3,7 @@
|
||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
using System;
|
using System;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using System.IO;
|
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using RunProcessAsTask;
|
|
||||||
|
|
||||||
namespace FFMpegCore.FFMPEG
|
namespace FFMpegCore.FFMPEG
|
||||||
{
|
{
|
||||||
|
|
|
@ -11,6 +11,7 @@
|
||||||
<AssemblyVersion>1.0.12.0</AssemblyVersion>
|
<AssemblyVersion>1.0.12.0</AssemblyVersion>
|
||||||
<FileVersion>1.0.12.0</FileVersion>
|
<FileVersion>1.0.12.0</FileVersion>
|
||||||
<PackageReleaseNotes></PackageReleaseNotes>
|
<PackageReleaseNotes></PackageReleaseNotes>
|
||||||
|
<LangVersion>8</LangVersion>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
@ -128,6 +129,7 @@
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
<PackageReference Include="Instances" Version="1.1.0" />
|
||||||
<PackageReference Include="Microsoft.CSharp" Version="4.5.0" />
|
<PackageReference Include="Microsoft.CSharp" Version="4.5.0" />
|
||||||
<PackageReference Include="Newtonsoft.Json" Version="12.0.2" />
|
<PackageReference Include="Newtonsoft.Json" Version="12.0.2" />
|
||||||
<PackageReference Include="RunProcessAsTask" Version="1.2.4" />
|
<PackageReference Include="RunProcessAsTask" Version="1.2.4" />
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
using FFMpegCore.FFMPEG.Exceptions;
|
using FFMpegCore.FFMPEG.Exceptions;
|
||||||
|
|
||||||
namespace FFMpegCore.Helpers
|
namespace FFMpegCore.Helpers
|
||||||
|
|
|
@ -1,7 +1,4 @@
|
||||||
using System;
|
using FFMpegCore.FFMPEG.Exceptions;
|
||||||
using System.IO;
|
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
using FFMpegCore.FFMPEG.Exceptions;
|
|
||||||
|
|
||||||
namespace FFMpegCore.Helpers
|
namespace FFMpegCore.Helpers
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,10 +1,8 @@
|
||||||
using FFMpegCore.Enums;
|
using FFMpegCore.Enums;
|
||||||
using FFMpegCore.FFMPEG;
|
|
||||||
using FFMpegCore.Helpers;
|
using FFMpegCore.Helpers;
|
||||||
using System;
|
using System;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Linq;
|
|
||||||
|
|
||||||
namespace FFMpegCore
|
namespace FFMpegCore
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
# FFMpegCore
|
# FFMpegCore
|
||||||
[![NuGet Badge](https://buildstats.info/nuget/FFMpegCore)](https://www.nuget.org/packages/FFMpegCore/)
|
[![NuGet Badge](https://buildstats.info/nuget/FFMpegCore)](https://www.nuget.org/packages/FFMpegCore/)
|
||||||
[![Build Status](https://travis-ci.org/vladjerca/FFMpegCore.svg?branch=master)](https://travis-ci.org/vladjerca/FFMpegCore)
|
[![Build Status](https://travis-ci.org/rosenbjerg/FFMpegCore.svg)](https://travis-ci.org/vladjerca/FFMpegCore)
|
||||||
|
|
||||||
# Setup
|
# Setup
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue