feat: add ffmpeg support for video analysis and screenshots
This commit is contained in:
parent
aa5c6d3f6d
commit
2bbbc32322
87
src/CasaBot/CasaBotApp/FFMPEGWrapper.cs
Normal file
87
src/CasaBot/CasaBotApp/FFMPEGWrapper.cs
Normal file
@ -0,0 +1,87 @@
|
||||
using Microsoft.Extensions.Logging;
|
||||
using System.Diagnostics;
|
||||
|
||||
namespace CasaBotApp;
|
||||
|
||||
public class FfmpegWrapper
|
||||
{
|
||||
private readonly ILogger<FfmpegWrapper> _logger;
|
||||
|
||||
public FfmpegWrapper(ILogger<FfmpegWrapper> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
private const string FFMPEG_PATH = @".\dvr-scanner\ffmpeg.exe";
|
||||
//Include method for get duration of a video, extract the frame at a specific time
|
||||
|
||||
public async Task<TimeSpan> GetVideoDuration(string videoPath)
|
||||
{
|
||||
try
|
||||
{
|
||||
_logger.LogDebug("Getting video duration...");
|
||||
var ffmpegProcess = new Process
|
||||
{
|
||||
StartInfo = new ProcessStartInfo
|
||||
{
|
||||
FileName = FFMPEG_PATH,
|
||||
Arguments = $"-i {videoPath}",
|
||||
RedirectStandardOutput = false,
|
||||
UseShellExecute = false,
|
||||
CreateNoWindow = true,
|
||||
RedirectStandardError = true
|
||||
}
|
||||
};
|
||||
ffmpegProcess.Start();
|
||||
|
||||
var standardError = await ffmpegProcess.StandardError.ReadToEndAsync();
|
||||
await ffmpegProcess.WaitForExitAsync();
|
||||
|
||||
// Parse the duration from the ffmpeg output
|
||||
var durationString = System.Text.RegularExpressions.Regex.Match(standardError, @"Duration: (\d{2}):(\d{2}):(\d{2})\.(\d{2})").Groups;
|
||||
var ts = new TimeSpan(0,
|
||||
int.Parse(durationString[1].Value),
|
||||
int.Parse(durationString[2].Value),
|
||||
int.Parse(durationString[3].Value),
|
||||
int.Parse(durationString[4].Value) * 10
|
||||
);
|
||||
return ts;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex, "An error occurred while getting the video duration");
|
||||
throw new Exception("There was an error getting the video duration", ex);
|
||||
}
|
||||
}
|
||||
|
||||
public async Task ExtractFrame(string videoPath, string outputPath, TimeSpan time)
|
||||
{
|
||||
try
|
||||
{
|
||||
var timeParam = $"{time.Minutes:D2}:{time.Seconds:D2}.{time.Milliseconds:D2}";
|
||||
_logger.LogDebug("Extracting frame: {videoPath} at {time} to {outputPath}", videoPath, timeParam, outputPath);
|
||||
var ffmpegProcess = new Process
|
||||
{
|
||||
StartInfo = new ProcessStartInfo
|
||||
{
|
||||
FileName = FFMPEG_PATH,
|
||||
Arguments = $"-y -i {videoPath} -ss {timeParam} -vframes 1 {outputPath}",
|
||||
RedirectStandardOutput = false,
|
||||
UseShellExecute = false,
|
||||
CreateNoWindow = true,
|
||||
RedirectStandardError = false
|
||||
}
|
||||
};
|
||||
ffmpegProcess.Start();
|
||||
_logger.LogDebug("Waiting for frame extraction... process ID: {Id}", ffmpegProcess.Id);
|
||||
await ffmpegProcess.WaitForExitAsync();
|
||||
_logger.LogInformation("Frame extracted successfully!");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex, "An error occurred while extracting the frame");
|
||||
throw new Exception("There was an error extracting the frame", ex);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user