/// <summary> /// /// </summary> /// <param name="file"></param> /// <param name="progress"></param> /// <returns></returns> public async Task <MediaJob> Work(FileInfo file, ProgressWorker progress, bool thumb, bool icon) { MediaJob mediaJobData = new MediaJob(); // Load the image and get metadata using MagickImage image = new MagickImage(file.FullName); mediaJobData.File = file; mediaJobData.Updated = file.LastWriteTime; mediaJobData.Width = image.Width; mediaJobData.Height = image.Height; mediaJobData.Duration = 0; Dictionary <string, string> metaDic = metaDic = Media.GetMeta(file); mediaJobData.Title = metaDic.ContainsKey("Object Name") ? metaDic["Object Name"] : file.Name; mediaJobData.Caption = metaDic.ContainsKey("Caption/Abstract") ? metaDic["Caption/Abstract"] : mediaJobData.Caption; // Make the thumbnail if (thumb) { mediaJobData.Thumbnail = true; await Task.Run(() => { Media.Dimension imageCrop = null; if (Configuration.Get.UseFaceDetector) { // Check for faces Media.Dimension face = Media.GetFaceCrop(file, image.Width, image.Height); if (face != null) // If a face was detected, put it as the image crop { imageCrop = face; } } if (imageCrop == null) // If no image crop is defined, use the default crop { // Compute new dimensions imageCrop = Media.GetCroppedThumbnailDimensions(image.Width, image.Height, true); } // Crop image image.Crop(new MagickGeometry(imageCrop.CropLeft, imageCrop.CropTop, imageCrop.CropWidth, imageCrop.CropHeight)); // Resize image to thumbnail MagickGeometry thumbSize = new MagickGeometry(imageCrop.Width, imageCrop.Height); thumbSize.IgnoreAspectRatio = false; image.Resize(thumbSize); // Write the thumbnail to disk using (FileStream writeStream = file.GetAlternateDataStream(Media.GetThumbName(file), FileMode.Create).OpenWrite()) { image.Write(writeStream); writeStream.Close(); } progress.FinishedWork(Media.GetThumbName(file)); }); } if (icon) { mediaJobData.Icon = true; await Task.Run(() => { // Resize image to icon MagickGeometry iconSize = new MagickGeometry(Configuration.Get.Image.Icon.Width, Configuration.Get.Image.Icon.Height); iconSize.IgnoreAspectRatio = false; image.Resize(iconSize); // Write the icon to disk using (FileStream writeStream = file.GetAlternateDataStream(Media.GetIconName(file), FileMode.Create).OpenWrite()) { image.Write(writeStream); writeStream.Close(); } progress.FinishedWork(Media.GetIconName(file)); }); } return(mediaJobData); }
/// <summary> /// /// </summary> /// <param name="file"></param> /// <param name="progress"></param> /// <returns></returns> public async Task <MediaJob> Work(FileInfo file, ProgressWorker progress, bool thumb, bool icon) { MediaJob mediaJobData = new MediaJob(); Dictionary <string, string> metaData = new Dictionary <string, string>(); IMediaInfo mediaInfo = await FFmpeg.GetMediaInfo(file.FullName); IVideoStream videoStream = mediaInfo.VideoStreams.FirstOrDefault(); IVideoStream pictureStream = mediaInfo.VideoStreams.FirstOrDefault(); string thumbTempFile = Path.Combine(Configuration.Get.TempDir, Guid.NewGuid() + "_" + Media.GetThumbName(file)); string iconTempFile = Path.Combine(Configuration.Get.TempDir, Guid.NewGuid() + "_" + Media.GetIconName(file)); Func <string, string> iconTempFileFunc = (number) => { return("\"" + iconTempFile.Replace("\\", "\\\\") + "\""); }; // Fill out metadata Dictionary <string, string> metaDic = metaDic = Media.GetMeta(file); mediaJobData.Title = metaDic.ContainsKey("Object Name") ? metaDic["Object Name"] : file.Name; mediaJobData.Caption = metaDic.ContainsKey("Caption/Abstract") ? metaDic["Caption"] : mediaJobData.Caption; mediaJobData.File = file; mediaJobData.Updated = file.LastWriteTime; mediaJobData.Width = videoStream.Width; mediaJobData.Height = videoStream.Height; mediaJobData.Duration = videoStream.Duration.TotalSeconds; // Calculate the thumbnail clip start and length double clipStart = Configuration.Get.Video.ClipStart; double clipLength = Configuration.Get.Video.ClipLength; double duration = videoStream.Duration.TotalSeconds; if (clipStart + clipLength > duration) { clipStart = 0; // Requested clip exceeds video file's duration } if (clipStart + clipLength > duration) { clipLength = duration; // Extremely short video file } // Set up the video thumbnail conversion if (thumb) { Media.Dimension d = Media.GetCroppedThumbnailDimensions(videoStream.Width, videoStream.Height, false); mediaJobData.Thumbnail = true; IConversion thumbConversion = FFmpeg.Conversions.New() .AddStream(videoStream) .SetSeek(TimeSpan.FromSeconds(clipStart)) .SetOutputTime(TimeSpan.FromSeconds(clipLength)) .SetOutputFormat(Format.mp4) .SetVideoBitrate(60000) .AddParameter("-s " + ((int)d.Width).ToString() + "x" + ((int)d.Height).ToString()) .AddParameter("-vcodec libx264") .AddParameter("-pix_fmt yuv420p") .SetOutput(thumbTempFile); // Do the thumbnail conversion _ = thumbConversion.Start().ContinueWith((result) => { using (FileStream input = File.OpenRead(thumbTempFile)) using (FileStream output = file.GetAlternateDataStream(Media.GetThumbName(file), FileMode.Create).OpenWrite()) { int bufferLength = 1024; byte[] buffer = new byte[bufferLength]; int bytesRead = 0; do { bytesRead = input.Read(buffer, 0, bufferLength); output.Write(buffer, 0, bytesRead); }while (bytesRead != 0); } File.Delete(thumbTempFile); progress.FinishedWork(Media.GetThumbPath(file)); }); } if (icon) { mediaJobData.Icon = true; // Set up the icon conversion pictureStream.SetCodec(VideoCodec.png); IConversion iconConversion = FFmpeg.Conversions.New() .AddStream(pictureStream) .ExtractNthFrame(1, iconTempFileFunc) .AddParameter("-s " + (Configuration.Get.Image.Icon.Width).ToString() + "x" + ((int)(((double)Configuration.Get.Image.Icon.Width / (double)videoStream.Width) * (double)videoStream.Height)).ToString()); // Do the icon conversion _ = iconConversion.Start().ContinueWith((result) => { using (FileStream input = File.OpenRead(iconTempFile)) using (FileStream output = file.GetAlternateDataStream(Media.GetIconName(file), FileMode.Create).OpenWrite()) { int bufferLength = 1024; byte[] buffer = new byte[bufferLength]; int bytesRead = 0; do { bytesRead = input.Read(buffer, 0, bufferLength); output.Write(buffer, 0, bytesRead); }while (bytesRead != 0); } File.Delete(iconTempFile); progress.FinishedWork(Media.GetIconPath(file)); }); } // Done return(mediaJobData); }