public void CreateThumbnail(
            ThumbnailSheetCreateRequest request,
            Response response,
            TimeSpan currentPointInVideo,
            string outputFilepath)
        {
            var arguments = $"-i \"{request.VideoPath}\" -ss {currentPointInVideo} -vframes 1 {outputFilepath}";
            var app       = new CommandLineApplication();
            var result    = app.Run(_config.FfmpegPath, arguments);
            var errorInfo = result.ErrorData.Trim();

            // Success means that the thumbnail is created.
            if (File.Exists(outputFilepath))
            {
                return;
            }

            // lock is requried because we are accessing the response properties on more than one thread
            lock (Lock)
            {
                response.FfmpegArguments   = arguments;
                response.FfmpegErrorOutput = errorInfo;
                throw new HqvException($"No thumbnail created using ffmpeg for {outputFilepath}");
            }
        }
 private void AddTimeStamps(ThumbnailSheetCreateRequest request, List <ThumbnailInfo> thumbnailsSettings)
 {
     Parallel.ForEach(thumbnailsSettings, thumbnailsSetting =>
     {
         _timeStamper.Stamp(request, thumbnailsSetting.OutputFilepath, thumbnailsSetting.PointInVideo);
     });
 }
        public void CreateThumbnails(ThumbnailSheetCreateRequest request, Response response)
        {
            _request  = request;
            _response = response;
            var secondPerThumbnail = request.VideoDurationInSeconds / request.NumberOfThumbnails;
            var timespanToAdd      = TimeSpan.FromSeconds(secondPerThumbnail);
            // start at the halfway point from beginning and timespan to add. Should give us good thumbnails
            var currentPointInVideo = TimeSpan.FromSeconds(secondPerThumbnail / 2);

            var thumbnailsSettings = new List <ThumbnailInfo>();

            for (var currentThumbnailNumber = 1; currentThumbnailNumber <= request.NumberOfThumbnails; ++currentThumbnailNumber)
            {
                var outputFilepath = $"{_config.TempThumbnailPath}\\thumbnail-{currentThumbnailNumber:D3}.png";
                thumbnailsSettings.Add(new ThumbnailInfo(outputFilepath, currentPointInVideo));
                currentPointInVideo = currentPointInVideo.Add(timespanToAdd);
            }

            Parallel.ForEach(thumbnailsSettings, thumbnailsSetting =>
            {
                var tc = new FfmpegThumbnailCreatorExactLocation(_config);
                tc.CreateThumbnail(_request, _response, thumbnailsSetting.PointInVideo, thumbnailsSetting.OutputFilepath);
            });

            if (request.ShouldAddTimestamps)
            {
                AddTimeStamps(request, thumbnailsSettings);
            }
        }
Beispiel #4
0
 public void CreateSheet(ThumbnailSheetCreateRequest request, Response response)
 {
     using (var images = new MagickImageCollection())
     {
         CreateSheet(request, response, images);
     }
 }
Beispiel #5
0
 private void CreateTry(ThumbnailSheetCreateRequest request)
 {
     ValidateRequest(request);
     CleanupTempFolder();
     _thumbnailCreator.CreateThumbnails(request, _response);
     _sheetCreator.CreateSheet(request, _response);
     CleanupTempFolder();
 }
Beispiel #6
0
 private void GivenAValidRequest()
 {
     _request = new ThumbnailSheetCreateRequest(
         videoPath: @"C:\Workspace\media-tools-space\test-files\JLT.mp4",
         sheetName: "JLT",
         numberOfThumbnails: 16,
         videoDurationInSeconds: 152,
         sheetQuality: 80,
         sheetTitleFontSize: 12,
         thumbnailWidth: 320);
 }
Beispiel #7
0
        private static void ValidateRequest(ThumbnailSheetCreateRequest request)
        {
            var validator        = new ThumbnailSheetCreateRequestValidator();
            var validationResult = validator.Validate(request);

            if (validationResult.IsValid)
            {
                return;
            }

            var exception = new HqvException("Validation on request failed");

            exception.Data["errors"] = validationResult.Errors;
            throw exception;
        }
Beispiel #8
0
 /// <inheritdoc />
 /// <summary>
 /// Create a thumbnail sheet
 /// </summary>
 /// <param name="request">Request</param>
 /// <returns>Response</returns>
 public ThumbnailSheetCreateResponse Create(ThumbnailSheetCreateRequest request)
 {
     _response = new Response(request);
     try
     {
         CreateTry(request);
     }
     catch (HqvException ex)
     {
         _response.AddError(ex);
     }
     catch (Exception ex)
     {
         const string message = "Unhandled exception in ThumbnailSheetCreationService";
         _response.AddError(new Exception(message, ex));
     }
     return(_response);
 }
Beispiel #9
0
        private ThumbnailSheetCreateResponse CreateThumbnailSheet(CreateThumbnailSheetOptions options, VideoFileInformationModel videoFileInformation)
        {
            var request = new ThumbnailSheetCreateRequest(
                videoPath: options.VideoFilePath,
                sheetName: Path.GetFileNameWithoutExtension(options.VideoFilePath),
                numberOfThumbnails: options.NumberOfThumbnails,
                videoDurationInSeconds: videoFileInformation.DurationInSecs,
                correlationId: _correlationId);
            var response = _thumbnailSheetCreationService.Create(request);

            if (response.IsValid)
            {
                _auditor.AuditSuccess("VideoFile", options.VideoFilePath, "ThumbnailSheetCreated", response);
            }
            else
            {
                _auditor.AuditFailure("VideoFile", options.VideoFilePath, "ThumbnailSheetCreationFailed", response);
            }
            return(response);
        }
Beispiel #10
0
        public void Stamp(ThumbnailSheetCreateRequest request, string filePath, TimeSpan time)
        {
            var stampText    = time.ToString(request.VideoDurationInSeconds >= 3600 ? @"hh\:mm\:ss" : @"mm\:ss");
            var tempFilePath = filePath + ".tmp.png";

            using (var imgText = new MagickImage(filePath))
            {
                var drawable    = new DrawableText(5, 5, stampText);
                var gravity     = new DrawableGravity(Gravity.Southeast);
                var font        = new DrawableFont("Tahoma");
                var antialias   = new DrawableTextAntialias(true);
                var size        = new DrawableFontPointSize(48);
                var color       = new DrawableFillColor(MagickColors.Black);
                var strokecolor = new DrawableStrokeColor(MagickColors.AliceBlue);
                imgText.Draw(drawable, gravity, font, antialias, size, color, strokecolor);
                imgText.Write(tempFilePath);
            }

            File.Delete(filePath);
            File.Move(tempFilePath, filePath);
        }
Beispiel #11
0
        private void CreateSheet(ThumbnailSheetCreateRequest request, Response response, IMagickImageCollection images)
        {
            int tempWidth = 0, tempHeight = 0;
            var files = Directory.GetFiles(_config.TempThumbnailPath, "thumbnail*.png").OrderBy(x => x).ToList();

            foreach (var file in files)
            {
                var image = new MagickImage(file);
                tempWidth  = image.Width;
                tempHeight = image.Height;
                images.Add(image);
            }

            var conversionNumber = tempWidth / request.ThumbnailWidth;

            tempHeight = tempHeight / conversionNumber;

            var montageSetting = new MontageSettings
            {
                Geometry        = new MagickGeometry(request.ThumbnailWidth, tempHeight),
                TileGeometry    = new MagickGeometry(GetTileGeometry(files.Count)),
                BackgroundColor = MagickColors.Black,
                BorderColor     = MagickColors.DarkGray,
                BorderWidth     = 1,
                Font            = "Arial",
                FontPointsize   = request.SheetTitleFontSize,
                FillColor       = MagickColors.LightGray,
                StrokeColor     = MagickColors.WhiteSmoke,
                Title           = request.SheetName
            };

            using (var montage = images.Montage(montageSetting))
            {
                var path = Path.Combine(_config.ThumbnailSheetPath, request.SheetName + "-sheet.jpg");
                montage.Format  = MagickFormat.Jpeg;
                montage.Quality = request.SheetQuality;
                montage.Write(path);
                response.SheetFilePath = path;
            }
        }
Beispiel #12
0
 public Response(ThumbnailSheetCreateRequest request) : base(request)
 {
 }