public async Task <StorageFile> CropAsync() { var file = await ApplicationData.Current.TemporaryFolder.CreateFileAsync("crop.jpg", CreationCollisionOption.ReplaceExisting); using (var fileStream = await m_imageSource.OpenAsync(FileAccessMode.Read)) using (var outputStream = await file.OpenAsync(FileAccessMode.ReadWrite)) { var decoder = await BitmapDecoder.CreateAsync(fileStream); var bounds = new BitmapBounds(); bounds.X = (uint)CropRectangle.X; bounds.Y = (uint)CropRectangle.Y; bounds.Width = (uint)CropRectangle.Width; bounds.Height = (uint)CropRectangle.Height; var transform = ComputeScalingTransformForSourceImage(decoder); transform.Bounds = bounds; var pixelData = await decoder.GetSoftwareBitmapAsync(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(0.77, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, outputStream); encoder.SetSoftwareBitmap(pixelData); await encoder.FlushAsync(); } return(file); }
public async Task Save(double compression) { var picker = new FileSavePicker(); picker.FileTypeChoices.Add("Obraz JPEG", new[] { ".jpg" }); var file = await picker.PickSaveFileAsync(); if (file == null || _bitmap == null) { return; } using (var stream = await file.OpenAsync(FileAccessMode.ReadWrite)) { var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(compression / 10, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, stream, propertySet); encoder.BitmapTransform.InterpolationMode = BitmapInterpolationMode.NearestNeighbor; Stream pixelStream = _bitmap.PixelBuffer.AsStream(); byte[] pixels = new byte[pixelStream.Length]; await pixelStream.ReadAsync(pixels, 0, pixels.Length); encoder.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Premultiplied, (uint)_bitmap.PixelWidth, (uint)_bitmap.PixelHeight, 96, 96, pixels); await encoder.FlushAsync(); } }
private async Task SaveSoftwareBitmapToFile(SoftwareBitmap softwareBitmap, StorageFile outputFile) { using (IRandomAccessStream stream = await outputFile.OpenAsync(FileAccessMode.ReadWrite)) { var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(1.0, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, stream, propertySet); encoder.SetSoftwareBitmap(softwareBitmap); try { await encoder.FlushAsync(); } catch (Exception err) { const int WINCODEC_ERR_UNSUPPORTEDOPERATION = unchecked ((int)0x88982F81); switch (err.HResult) { case WINCODEC_ERR_UNSUPPORTEDOPERATION: // If the encoder does not support writing a thumbnail, then try again // but disable thumbnail generation. encoder.IsThumbnailGenerated = false; break; default: throw; } } } }
public async Task Initialize(VideoSetting videoSetting) { await CoreApplication.MainView.CoreWindow.Dispatcher.RunAndAwaitAsync(CoreDispatcherPriority.Normal, async() => { _threadsCount = videoSetting.UsedThreads; _stoppedThreads = videoSetting.UsedThreads; _lastFrameAdded.Start(); _imageQuality = new BitmapPropertySet(); var imageQualityValue = new BitmapTypedValue(videoSetting.VideoQuality, Windows.Foundation.PropertyType.Single); _imageQuality.Add("ImageQuality", imageQualityValue); _mediaCapture = new MediaCapture(); var frameSourceGroups = await MediaFrameSourceGroup.FindAllAsync(); var settings = new MediaCaptureInitializationSettings() { SharingMode = MediaCaptureSharingMode.ExclusiveControl, //With CPU the results contain always SoftwareBitmaps, otherwise with GPU //they preferring D3DSurface MemoryPreference = MediaCaptureMemoryPreference.Cpu, //Capture only video, no audio StreamingCaptureMode = StreamingCaptureMode.Video }; await _mediaCapture.InitializeAsync(settings); var mediaFrameSource = _mediaCapture.FrameSources.First().Value; var videoDeviceController = mediaFrameSource.Controller.VideoDeviceController; videoDeviceController.DesiredOptimization = Windows.Media.Devices.MediaCaptureOptimization.Quality; videoDeviceController.PrimaryUse = Windows.Media.Devices.CaptureUse.Video; //Set exposure (auto light adjustment) if (_mediaCapture.VideoDeviceController.Exposure.Capabilities.Supported && _mediaCapture.VideoDeviceController.Exposure.Capabilities.AutoModeSupported) { _mediaCapture.VideoDeviceController.Exposure.TrySetAuto(true); } var videoResolutionWidthHeight = VideoResolutionWidthHeight.Get(videoSetting.VideoResolution); var videoSubType = VideoSubtypeHelper.Get(videoSetting.VideoSubtype); //Set resolution, frame rate and video subtyp var videoFormat = mediaFrameSource.SupportedFormats.Where(sf => sf.VideoFormat.Width == videoResolutionWidthHeight.Width && sf.VideoFormat.Height == videoResolutionWidthHeight.Height && sf.Subtype == videoSubType) .OrderByDescending(m => m.FrameRate.Numerator / m.FrameRate.Denominator) .First(); await mediaFrameSource.SetFormatAsync(videoFormat); _mediaFrameReader = await _mediaCapture.CreateFrameReaderAsync(mediaFrameSource); await _mediaFrameReader.StartAsync(); }); }
public static async Task <IRandomAccessStream> ImageToJPegStreamAsync(IRandomAccessStream imageStream) { //Create a decoder for the image var decoder = await BitmapDecoder.CreateAsync(imageStream); PixelDataProvider pixelData = await decoder.GetPixelDataAsync(); byte[] pixelBytes = pixelData.DetachPixelData(); // InMemoryRandomAccessStream jpegStream = new InMemoryRandomAccessStream(); double jpegImageQuality = 0.9; var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(jpegImageQuality, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, jpegStream, propertySet); //key thing here is to use decoder.OrientedPixelWidth and decoder.OrientedPixelHeight otherwise you will get garbled image on devices on some photos with orientation in metadata encoder.SetPixelData(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, decoder.OrientedPixelWidth, decoder.OrientedPixelHeight, decoder.DpiX, decoder.DpiY, pixelBytes); //ulong jpegImageSize = 0; //jpegImageSize = jpegStream.Size; await encoder.FlushAsync(); await jpegStream.FlushAsync(); return(jpegStream); }
public static async Task <ImageSource> CropAndPreviewAsync(IRandomAccessStream imageStream, Rect cropRectangle) { var decoder = await BitmapDecoder.CreateAsync(imageStream); var bounds = new BitmapBounds(); bounds.X = (uint)cropRectangle.X; bounds.Y = (uint)cropRectangle.Y; bounds.Width = (uint)cropRectangle.Width; bounds.Height = (uint)cropRectangle.Height; var transform = ComputeScalingTransformForSourceImage(decoder); transform.Bounds = bounds; var pixelData = await decoder.GetSoftwareBitmapAsync(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(0.77, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var bitmap = await decoder.GetSoftwareBitmapAsync(decoder.BitmapPixelFormat, BitmapAlphaMode.Premultiplied, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); var bitmapImage = new SoftwareBitmapSource(); await bitmapImage.SetBitmapAsync(bitmap); return(bitmapImage); }
private async Task makeJpegAsync(BitmapDecoder decoder, byte[] pixelBytes, pdfPage page, BitmapImage bitmapImage, int x, int y) { //double jpegImageQuality = Constants.ImageAttachStartingImageQuality; double jpegImageQuality = 0.9; ulong jpegImageSize = 0; var imageWriteableStream = new InMemoryRandomAccessStream(); //MemoryStream memoryStream = new MemoryStream(); //var imageWriteableStream = memoryStream.AsRandomAccessStream(); using (imageWriteableStream) { var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(jpegImageQuality, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, imageWriteableStream, propertySet); //key thing here is to use decoder.OrientedPixelWidth and decoder.OrientedPixelHeight otherwise you will get garbled image on devices on some photos with orientation in metadata encoder.SetPixelData(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, decoder.OrientedPixelWidth, decoder.OrientedPixelHeight, decoder.DpiX, decoder.DpiY, pixelBytes); jpegImageSize = imageWriteableStream.Size; await encoder.FlushAsync(); await imageWriteableStream.FlushAsync(); var byteArray = new byte[imageWriteableStream.Size]; await imageWriteableStream.ReadAsync(byteArray.AsBuffer(), (uint)imageWriteableStream.Size, InputStreamOptions.None); //page.addImage(bitmapImage, byteArray, x, y); page.addImage(imageWriteableStream); } }
private async Task ThumbnailTranscodeAsync(UpdateFileGenerationStart update, string[] args) { try { var conversion = JsonConvert.DeserializeObject<VideoConversion>(args[2]); //if (conversion.Transcode) { var file = await StorageApplicationPermissions.FutureAccessList.GetFileAsync(args[0]); var temp = await StorageFile.GetFileFromPathAsync(update.DestinationPath); var props = await file.Properties.GetVideoPropertiesAsync(); double originalWidth = props.GetWidth(); double originalHeight = props.GetHeight(); //if (!conversion.CropRectangle.IsEmpty()) //{ // file = await ImageHelper.CropAsync(file, temp, conversion.CropRectangle); // originalWidth = conversion.CropRectangle.Width; // originalHeight = conversion.CropRectangle.Height; //} using (var fileStream = await ImageHelper.OpenReadAsync(file)) using (var outputStream = await temp.OpenAsync(FileAccessMode.ReadWrite)) { var decoder = await BitmapDecoder.CreateAsync(fileStream); double ratioX = (double)90 / originalWidth; double ratioY = (double)90 / originalHeight; double ratio = Math.Min(ratioX, ratioY); uint width = (uint)(originalWidth * ratio); uint height = (uint)(originalHeight * ratio); var transform = new BitmapTransform(); transform.ScaledWidth = width; transform.ScaledHeight = height; transform.InterpolationMode = BitmapInterpolationMode.Linear; transform.Flip = conversion.Mirror == MediaMirroringOptions.Horizontal ? BitmapFlip.Horizontal : BitmapFlip.None; var pixelData = await decoder.GetSoftwareBitmapAsync(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(0.77, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, outputStream); encoder.SetSoftwareBitmap(pixelData); await encoder.FlushAsync(); _protoService.Send(new FinishFileGeneration(update.GenerationId, null)); } } } catch (Exception ex) { _protoService.Send(new FinishFileGeneration(update.GenerationId, new Error(500, "FILE_GENERATE_LOCATION_INVALID " + ex.ToString()))); } }
public async Task SaveTags(IEnumerable <string> tags) { List <KeyValuePair <string, object> > list = new List <KeyValuePair <string, object> >(); var t = new BitmapTypedValue(string.Join(",", tags), Windows.Foundation.PropertyType.String); list.Add(new KeyValuePair <string, object>(SystemProperties.Comment, t)); await MetaData.SavePropertiesAsync(list.AsEnumerable()); }
private async Task <BitmapEncoder> CaptureView(FrameworkElement view, IRandomAccessStream stream) { int w = (int)view.ActualWidth; int h = (int)view.ActualHeight; if (w <= 0 || h <= 0) { throw new InvalidOperationException("Impossible to snapshot the view: view is invalid"); } RenderTargetBitmap targetBitmap = new RenderTargetBitmap(); await targetBitmap.RenderAsync(view, w, h); BitmapEncoder encoder; if (extension != "png") { var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(quality, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, stream, propertySet); } else { encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, stream); } var displayInformation = DisplayInformation.GetForCurrentView(); var pixelBuffer = await targetBitmap.GetPixelsAsync(); encoder.SetPixelData( BitmapPixelFormat.Bgra8, BitmapAlphaMode.Ignore, (uint)targetBitmap.PixelWidth, (uint)targetBitmap.PixelHeight, displayInformation.LogicalDpi, displayInformation.LogicalDpi, pixelBuffer.ToArray()); if (width != null && height != null && (width != w || height != h)) { encoder.BitmapTransform.ScaledWidth = (uint)width; encoder.BitmapTransform.ScaledWidth = (uint)height; } if (encoder == null) { throw new InvalidOperationException("Impossible to snapshot the view"); } await encoder.FlushAsync(); return(encoder); }
public async static Task <byte[]> ToByteArrayAsync(this WriteableBitmap image, Abstractions.ImageFormat format, int quality = 100) { byte[] resultArray = null; WriteableBitmap writeableBitmap = image; using (IRandomAccessStream ms = new InMemoryRandomAccessStream()) { try { byte[] bytes; using (Stream stream = image.PixelBuffer.AsStream()) { bytes = new byte[(uint)stream.Length]; await stream.ReadAsync(bytes, 0, bytes.Length); } BitmapPropertySet propertySet = new BitmapPropertySet(); BitmapTypedValue qualityValue = new BitmapTypedValue( quality * .01, Windows.Foundation.PropertyType.Single ); propertySet.Add("ImageQuality", qualityValue); BitmapEncoder encoder = null; if (format == Abstractions.ImageFormat.PNG) { encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, ms); } else { encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, ms, propertySet); } encoder.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Ignore, (uint)image.PixelWidth, (uint)image.PixelHeight, 96, 96, bytes); await encoder.FlushAsync(); resultArray = new byte[ms.AsStream().Length]; await ms.AsStream().ReadAsync(resultArray, 0, resultArray.Length); } catch (Exception e) { System.Diagnostics.Debug.WriteLine(e.Message); } } return(resultArray); }
/// <summary> /// Resizes and crops source file image so that resized image width/height are not larger than <param name="requestedMinSide"></param> /// </summary> /// <param name="sourceFile">Source StorageFile</param> /// <param name="resizedImageFile">Target StorageFile</param> /// <param name="requestedMinSide">Max width/height of the output image</param> /// <param name="quality">JPEG compression quality (0.77 for pictures, 0.87 for thumbnails)</param> /// <returns></returns> public static async Task <StorageFile> ScaleJpegAsync(StorageFile sourceFile, StorageFile resizedImageFile, int requestedMinSide = 1280, double quality = 0.77) { using (var imageStream = await sourceFile.OpenReadAsync()) { var decoder = await BitmapDecoder.CreateAsync(imageStream); if (decoder.FrameCount > 1) { throw new InvalidCastException(); } var originalPixelWidth = decoder.PixelWidth; var originalPixelHeight = decoder.PixelHeight; using (var resizedStream = await resizedImageFile.OpenAsync(FileAccessMode.ReadWrite)) { BitmapTransform transform; if (decoder.PixelWidth > requestedMinSide || decoder.PixelHeight > requestedMinSide) { double ratioX = (double)requestedMinSide / originalPixelWidth; double ratioY = (double)requestedMinSide / originalPixelHeight; double ratio = Math.Min(ratioX, ratioY); uint width = (uint)(originalPixelWidth * ratio); uint height = (uint)(originalPixelHeight * ratio); transform = new BitmapTransform { ScaledWidth = width, ScaledHeight = height, InterpolationMode = BitmapInterpolationMode.Linear }; } else { transform = new BitmapTransform(); } var pixelData = await decoder.GetSoftwareBitmapAsync(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(quality, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, resizedStream); encoder.SetSoftwareBitmap(pixelData); await encoder.FlushAsync(); } } return(resizedImageFile); }
public static async Task <StorageFile> CropAsync(StorageFile sourceFile, StorageFile file, Rect cropRectangle, int min = 1280, int max = 0, double quality = 0.77) { if (file == null) { file = await ApplicationData.Current.TemporaryFolder.CreateFileAsync("crop.jpg", CreationCollisionOption.ReplaceExisting); } using (var fileStream = await OpenReadAsync(sourceFile)) using (var outputStream = await file.OpenAsync(FileAccessMode.ReadWrite)) { var decoder = await BitmapDecoder.CreateAsync(fileStream); var cropWidth = (double)decoder.PixelWidth; var cropHeight = (double)decoder.PixelHeight; if (decoder.PixelWidth > 1280 || decoder.PixelHeight > 1280) { double ratioX = (double)1280 / cropWidth; double ratioY = (double)1280 / cropHeight; double ratio = Math.Min(ratioX, ratioY); cropWidth = cropWidth * ratio; cropHeight = cropHeight * ratio; } var(scaledCrop, scaledSize) = Scale(cropRectangle, new Size(cropWidth, cropHeight), new Size(decoder.PixelWidth, decoder.PixelHeight), min, max); var bounds = new BitmapBounds(); bounds.X = (uint)scaledCrop.X; bounds.Y = (uint)scaledCrop.Y; bounds.Width = (uint)scaledCrop.Width; bounds.Height = (uint)scaledCrop.Height; var transform = new BitmapTransform(); transform.ScaledWidth = (uint)scaledSize.Width; transform.ScaledHeight = (uint)scaledSize.Height; transform.Bounds = bounds; transform.InterpolationMode = BitmapInterpolationMode.Linear; var pixelData = await decoder.GetSoftwareBitmapAsync(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(quality, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, outputStream); encoder.SetSoftwareBitmap(pixelData); await encoder.FlushAsync(); } return(file); }
private async void SaveSoftwareBitmapToFile(SoftwareBitmap softwareBitmap, StorageFile outputFile) { using (IRandomAccessStream stream = await outputFile.OpenAsync(FileAccessMode.ReadWrite)) { // Set properties var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue( 1.0, // Maximum quality Windows.Foundation.PropertyType.Single ); propertySet.Add("ImageQuality", qualityValue); // Create an encoder with the desired format BitmapEncoder encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, stream, propertySet); // Set the software bitmap encoder.SetSoftwareBitmap(softwareBitmap); //// Set additional encoding parameters, if needed //encoder.BitmapTransform.ScaledWidth = 320; //encoder.BitmapTransform.ScaledHeight = 240; //encoder.BitmapTransform.Rotation = Windows.Graphics.Imaging.BitmapRotation.Clockwise90Degrees; //encoder.BitmapTransform.InterpolationMode = BitmapInterpolationMode.Fant; encoder.IsThumbnailGenerated = true; try { await encoder.FlushAsync(); } catch (Exception err) { const int WINCODEC_ERR_UNSUPPORTEDOPERATION = unchecked ((int)0x88982F81); switch (err.HResult) { case WINCODEC_ERR_UNSUPPORTEDOPERATION: // If the encoder does not support writing a thumbnail, then try again // but disable thumbnail generation. encoder.IsThumbnailGenerated = false; break; default: throw; } } //throwing error? if (encoder.IsThumbnailGenerated == false) { await encoder.FlushAsync(); } } }
/// <summary> /// Converts source image file to jpeg of defined quality (0.85) /// </summary> /// <param name="sourceFile">Source StorageFile</param> /// <param name="outputFile">Target StorageFile</param> /// <returns></returns> private async Task <StorageFile> ConvertImageToJpegAsync(StorageFile sourceFile, StorageFile outputFile) { //you can use WinRTXamlToolkit StorageItemExtensions.GetSizeAsync to get file size (if you already plugged this nuget in) var sourceFileProperties = await sourceFile.GetBasicPropertiesAsync(); var fileSize = sourceFileProperties.Size; var imageStream = await sourceFile.OpenReadAsync(); Stopwatch stopwatch = new Stopwatch(); stopwatch.Start(); using (imageStream) { var decoder = await BitmapDecoder.CreateAsync(imageStream); var pixelData = await decoder.GetPixelDataAsync(); var detachedPixelData = pixelData.DetachPixelData(); pixelData = null; //0.85d //double jpegImageQuality = Constants.ImageAttachStartingImageQuality; double jpegImageQuality = 0.9; //since we're using MvvmCross, we're outputing diagnostic info to MvxTrace, you can use System.Diagnostics.Debug.WriteLine instead //Mvx.TaggedTrace(MvxTraceLevel.Diagnostic, "ImageService", $"Source image size: {fileSize}, trying Q={jpegImageQuality}"); var imageWriteableStream = await outputFile.OpenAsync(FileAccessMode.ReadWrite); ulong jpegImageSize = 0; using (imageWriteableStream) { var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(jpegImageQuality, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, imageWriteableStream, propertySet); //key thing here is to use decoder.OrientedPixelWidth and decoder.OrientedPixelHeight otherwise you will get garbled image on devices on some photos with orientation in metadata encoder.SetPixelData(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, decoder.OrientedPixelWidth, decoder.OrientedPixelHeight, decoder.DpiX, decoder.DpiY, detachedPixelData); await encoder.FlushAsync(); await imageWriteableStream.FlushAsync(); jpegImageSize = imageWriteableStream.Size; } //Mvx.TaggedTrace(MvxTraceLevel.Diagnostic, "ImageService", $"Final image size now: {jpegImageSize}"); } stopwatch.Stop(); //Mvx.TaggedTrace(MvxTraceLevel.Diagnostic, "ImageService", $"Time spent optimizing image: {stopwatch.Elapsed}"); return(outputFile); }
private async void MainPage_Loaded(object sender, RoutedEventArgs e) { await Task.Delay(TimeSpan.FromSeconds(1)); var renderTargetBitmap = new RenderTargetBitmap(); await renderTargetBitmap.RenderAsync(Grid); var pngFile = await ApplicationData.Current.TemporaryFolder.CreateFileAsync(Path.GetRandomFileName() + ".jpg"); using (var pngStream = await pngFile.OpenStreamForWriteAsync()) { BitmapPropertySet propertySet = new BitmapPropertySet(); BitmapTypedValue qualityValue = new BitmapTypedValue(0.77, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, pngStream.AsRandomAccessStream(), propertySet); // https://docs.microsoft.com/en-us/windows/win32/properties/windows-properties-system?WT.mc_id=WD-MVP-5003260 propertySet = new BitmapPropertySet(); // 作者 propertySet.Add("System.Author", new BitmapTypedValue("lindexi", PropertyType.String)); // 相机型号 propertySet.Add("System.Photo.CameraModel", new BitmapTypedValue("lindexi", PropertyType.String)); // 制造商 propertySet.Add("System.Photo.CameraManufacturer", new BitmapTypedValue("lindexi manufacturer", PropertyType.String)); // 光圈值 System.Photo.FNumberNumerator/System.Photo.FNumberDenominator propertySet.Add("System.Photo.FNumberNumerator", new BitmapTypedValue(1, PropertyType.UInt32)); propertySet.Add("System.Photo.FNumberDenominator", new BitmapTypedValue(10, PropertyType.UInt32)); await encoder.BitmapProperties.SetPropertiesAsync(propertySet); var pixelBuffer = await renderTargetBitmap.GetPixelsAsync(); var softwareBitmap = SoftwareBitmap.CreateCopyFromBuffer(pixelBuffer, BitmapPixelFormat.Bgra8, renderTargetBitmap.PixelWidth, renderTargetBitmap.PixelHeight); encoder.SetSoftwareBitmap(softwareBitmap); await encoder.FlushAsync(); softwareBitmap.Dispose(); } await Launcher.LaunchFolderAsync(ApplicationData.Current.TemporaryFolder); }
public async Task <BitmapEncoder> CreateOptimizedBitmapEncoderAsync(ImageScannerFormat?encoderFormat, IRandomAccessStream stream) { // get encoder ID Guid encoderId; switch (encoderFormat) { case ImageScannerFormat.Jpeg: encoderId = BitmapEncoder.JpegEncoderId; break; case ImageScannerFormat.Png: encoderId = BitmapEncoder.PngEncoderId; break; case ImageScannerFormat.Tiff: encoderId = BitmapEncoder.TiffEncoderId; break; case ImageScannerFormat.DeviceIndependentBitmap: encoderId = BitmapEncoder.BmpEncoderId; break; default: throw new ApplicationException($"CreateOptimizedBitmapEncoderAsync received invalid ImageScannerFormat {encoderFormat}"); } // create encoder if (encoderFormat == ImageScannerFormat.Jpeg) { // prevent large JPG size var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(0.85d, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); stream.Size = 0; return(await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, stream, propertySet)); } else { return(await BitmapEncoder.CreateAsync(encoderId, stream)); } }
/// <summary> /// 将原来的图片转换图片质量和压缩质量 /// </summary> /// <param name="sourceFile">原来的图片</param> /// <param name="outputFile">输出的文件</param> /// <param name="imageQuality">图片质量,取值范围是 0 到 1 其中 1 的质量最好,这个值设置只对 jpg 图片有效</param> /// <returns></returns> private async Task <StorageFile> ConvertImageToJpegAsync(StorageFile sourceFile, StorageFile outputFile, double imageQuality) { var sourceFileProperties = await sourceFile.GetBasicPropertiesAsync(); var fileSize = sourceFileProperties.Size; var imageStream = await sourceFile.OpenReadAsync(); using (imageStream) { var decoder = await BitmapDecoder.CreateAsync(imageStream); var pixelData = await decoder.GetPixelDataAsync(); var detachedPixelData = pixelData.DetachPixelData(); var imageWriteAbleStream = await outputFile.OpenAsync(FileAccessMode.ReadWrite); using (imageWriteAbleStream) { var propertySet = new BitmapPropertySet(); // 图片质量,值范围是 0到1 其中 1 的质量最好 var qualityValue = new BitmapTypedValue(imageQuality, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, imageWriteAbleStream, propertySet); //key thing here is to use decoder.OrientedPixelWidth and decoder.OrientedPixelHeight otherwise you will get garbled image on devices on some photos with orientation in metadata encoder.SetPixelData(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, decoder.OrientedPixelWidth, decoder.OrientedPixelHeight, decoder.DpiX, decoder.DpiY, detachedPixelData); await encoder.FlushAsync(); await imageWriteAbleStream.FlushAsync(); var jpegImageSize = imageWriteAbleStream.Size; // 欢迎访问我博客 https://blog.lindexi.com/ 里面有大量 UWP WPF 博客 Debug.WriteLine($"压缩之后比压缩前的文件小{fileSize - jpegImageSize}"); } } return(outputFile); }
/// <summary> /// Saves a SoftwareBitmap to the specified StorageFile /// </summary> /// <param name="bitmap">SoftwareBitmap to save</param> /// <param name="file">Target StorageFile to save to</param> /// <returns></returns> private static async Task SaveSoftwareBitmapAsync(SoftwareBitmap bitmap, StorageFile file) { using (var outputStream = await file.OpenAsync(FileAccessMode.ReadWrite)) { var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, outputStream); var propertySet = new BitmapPropertySet(); var orientationValue = new BitmapTypedValue( 1, // Defined as EXIF orientation = "normal" PropertyType.UInt16 ); propertySet.Add("System.Photo.Orientation", orientationValue); await encoder.BitmapProperties.SetPropertiesAsync(propertySet); // Grab the data from the SoftwareBitmap encoder.SetSoftwareBitmap(bitmap); await encoder.FlushAsync(); } }
private async Task <byte[]> Bitmap2JPEG(SoftwareBitmap bitmap) { // JPEG quality var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue( 0.67, // Maximum quality PropertyType.Single ); propertySet.Add("ImageQuality", qualityValue); // JPEG compression into memory var memStream = new InMemoryRandomAccessStream(); BitmapEncoder encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, memStream, propertySet); // the SetSoftwareBitmap may cause a memory leak, but only for debugging (it's a bug in VS) // See http://stackoverflow.com/questions/35528030/bitmapencoder-memoryleak-with-softwarebitmap encoder.SetSoftwareBitmap(bitmap); await encoder.FlushAsync(); // Send the data to network byte[] imageData; using (var inputStream = memStream.GetInputStreamAt(0)) { using (var dataReader = new DataReader(inputStream)) { // Once we have written the contents successfully we load the stream. await dataReader.LoadAsync((uint)memStream.Size); imageData = new byte[(uint)memStream.Size]; dataReader.ReadBytes(imageData); } } // Clean... memStream.Dispose(); return(imageData); }
public static async Task <Stream> AsJpegStreamAsync(this WriteableBitmap bitmap, int quality = 90) { byte[] pixels; using (var stream = bitmap.PixelBuffer.AsStream()) { pixels = new byte[(uint)stream.Length]; await stream.ReadAsync(pixels, 0, pixels.Length); } var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue((double)quality / 100d, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var raStream = new InMemoryRandomAccessStream(); // Encode pixels into stream var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, raStream, propertySet); encoder.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Premultiplied, (uint)bitmap.PixelWidth, (uint)bitmap.PixelHeight, 96, 96, pixels); await encoder.FlushAsync(); return(raStream.AsStreamForRead()); }
/// <summary> /// Method that will generate an ObjectState for the provided deck information. /// </summary> /// <param name="deckCardIds">List of strings representing card Ids.</param> /// <param name="strBackCard">Direct image url representing the back of the card.</param> /// <returns>A ObjectState representing the deck.</returns> private async Task <ObjectState> generateDeck(List <string> deckCardIds, string strBackCard) { // Generate WriteableBitmaps for deck. Guid BitmapEncoderGuid = BitmapEncoder.JpegEncoderId; WriteableBitmap deckBitmap = await generateWriteableBitmapForDeck(deckCardIds); //var file = await Windows.Storage.ApplicationData.Current.TemporaryFolder.CreateFileAsync("combine.jpg", CreationCollisionOption.ReplaceExisting); using (IRandomAccessStream stream = new InMemoryRandomAccessStream())//await file.OpenAsync(FileAccessMode.ReadWrite)) { BitmapPropertySet propertySet = new BitmapPropertySet(); BitmapTypedValue quality = new BitmapTypedValue(1.0, PropertyType.Single); propertySet.Add("ImageQuality", quality); BitmapEncoder encoder = await BitmapEncoder.CreateAsync(BitmapEncoderGuid, stream, propertySet); Stream pixelStream = deckBitmap.PixelBuffer.AsStream(); byte[] pixels = new byte[pixelStream.Length]; await pixelStream.ReadAsync(pixels, 0, pixels.Length); encoder.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Ignore, (uint)deckBitmap.PixelWidth, (uint)deckBitmap.PixelHeight, 96, 96, pixels); await encoder.FlushAsync(); // Upload WriteableBitmaps to Imgur and save their direct urls (requires Imgur API). string deckUrl = await uploadPhotoToImgur(stream); // Get list of card names for deck. List <string> deckCardNames = await generateCardNamesForDeck(deckCardIds); // Get the number of rows and columns that are in the WriteableBitmap. Tuple <int, int> deckSize = getDeckSize(deckCardIds); // Build out ObjectState objects for deck. ObjectState deckObjectState = buildObjectState(deckCardIds, deckSize, deckUrl, strBackCard, deckCardNames, 1); return(deckObjectState); } }
private async Task <Stream> ConvertToJpeg(IRandomAccessStream stream) { var decoder = await BitmapDecoder.CreateAsync(stream); var pixels = await decoder.GetPixelDataAsync(); var outStream = new InMemoryRandomAccessStream(); // create encoder for saving the tile image var propertySet = new BitmapPropertySet(); // create class representing target jpeg quality - a bit obscure, but it works var qualityValue = new BitmapTypedValue(.7, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, outStream); encoder.SetPixelData(decoder.BitmapPixelFormat, BitmapAlphaMode.Ignore, decoder.OrientedPixelWidth, decoder.OrientedPixelHeight, decoder.DpiX, decoder.DpiY, pixels.DetachPixelData()); await encoder.FlushAsync(); return(outStream.AsStream()); }
public static async Task <TLPhotoSizeBase> GetVideoThumbnailAsync(StorageFile file, VideoProperties props, VideoTransformEffectDefinition effect) { double originalWidth = props.GetWidth(); double originalHeight = props.GetHeight(); if (effect != null && !effect.CropRectangle.IsEmpty) { file = await CropAsync(file, effect.CropRectangle); originalWidth = effect.CropRectangle.Width; originalHeight = effect.CropRectangle.Height; } TLPhotoSizeBase result; var fileLocation = new TLFileLocation { VolumeId = TLLong.Random(), LocalId = TLInt.Random(), Secret = TLLong.Random(), DCId = 0 }; var desiredName = string.Format("{0}_{1}_{2}.jpg", fileLocation.VolumeId, fileLocation.LocalId, fileLocation.Secret); var desiredFile = await FileUtils.CreateTempFileAsync(desiredName); using (var fileStream = await OpenReadAsync(file)) using (var outputStream = await desiredFile.OpenAsync(FileAccessMode.ReadWrite)) { var decoder = await BitmapDecoder.CreateAsync(fileStream); double ratioX = (double)90 / originalWidth; double ratioY = (double)90 / originalHeight; double ratio = Math.Min(ratioX, ratioY); uint width = (uint)(originalWidth * ratio); uint height = (uint)(originalHeight * ratio); var transform = new BitmapTransform(); transform.ScaledWidth = width; transform.ScaledHeight = height; transform.InterpolationMode = BitmapInterpolationMode.Linear; if (effect != null) { transform.Flip = effect.Mirror == MediaMirroringOptions.Horizontal ? BitmapFlip.Horizontal : BitmapFlip.None; } var pixelData = await decoder.GetSoftwareBitmapAsync(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(0.77, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, outputStream); encoder.SetSoftwareBitmap(pixelData); await encoder.FlushAsync(); result = new TLPhotoSize { W = (int)width, H = (int)height, Size = (int)outputStream.Size, Type = string.Empty, Location = fileLocation }; } return(result); }
public async void HttpPost(string uid, string uimage, string name, string content, List <string> imagePsthList, string songPath, string date, int type) { NotifyControl notify = new NotifyControl(); notify.Text = "亲,努力发送中..."; notify.Show(); HttpClient httpClient = new HttpClient(); uint MaxImageWidth = 480; uint MaxImageHeight = 800; uint width; uint height; try { string posturi = Config.apiDreamingPublish; HttpMultipartFormDataContent fileContent = new HttpMultipartFormDataContent(); if (imagePsthList.Count > 0) { for (int i = 0; i < imagePsthList.Count; i++) { StorageFile inFile = await StorageFile.GetFileFromPathAsync(imagePsthList[i]); var inStream = await inFile.OpenReadAsync(); InMemoryRandomAccessStream outStream = new InMemoryRandomAccessStream(); BitmapDecoder decoder = await ImageHelp.GetProperDecoder(inStream, inFile); if (decoder == null) { return; } if (decoder.OrientedPixelWidth > MaxImageWidth && decoder.OrientedPixelHeight > MaxImageHeight) { width = MaxImageWidth; height = MaxImageHeight; } else { width = decoder.OrientedPixelWidth; height = decoder.OrientedPixelHeight; } PixelDataProvider provider = await decoder.GetPixelDataAsync(); byte[] data = provider.DetachPixelData(); //获取像素数据的字节数组 BitmapPropertySet propertySet = new BitmapPropertySet(); BitmapTypedValue qualityValue = new BitmapTypedValue(0.5, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, outStream, propertySet);//建立编码器 encoder.SetPixelData(decoder.BitmapPixelFormat, decoder.BitmapAlphaMode, decoder.OrientedPixelWidth, decoder.OrientedPixelHeight, decoder.DpiX, decoder.DpiY, data ); encoder.BitmapTransform.ScaledWidth = width; encoder.BitmapTransform.ScaledHeight = height; await encoder.FlushAsync(); HttpStreamContent streamContent1 = new HttpStreamContent(outStream); fileContent.Add(streamContent1, "pic", inFile.Name); } } if (songPath != null) { StorageFile file1 = await StorageFile.GetFileFromPathAsync(songPath); IRandomAccessStreamWithContentType stream1 = await file1.OpenReadAsync(); HttpStreamContent streamContent1 = new HttpStreamContent(stream1); fileContent.Add(streamContent1, "song", file1.Name); } HttpStringContent stringContent = new HttpStringContent(content); HttpStringContent stringName = new HttpStringContent(name); HttpStringContent stringUid = new HttpStringContent(uid); HttpStringContent stringUimage = new HttpStringContent(uimage); HttpStringContent stringTime = new HttpStringContent(date); HttpStringContent stringType = new HttpStringContent(type.ToString()); fileContent.Add(stringContent, "content"); fileContent.Add(stringUid, "phone"); fileContent.Add(stringUimage, "uimage"); fileContent.Add(stringName, "name"); fileContent.Add(stringTime, "time"); fileContent.Add(stringType, "type"); HttpResponseMessage response = await httpClient.PostAsync(new Uri(posturi), fileContent); Init(); notify.Hide(); PostCommand.CanExecutes = true; NavigationHelp.NavigateTo(typeof(AllDreaming)); } catch (Exception ex) { HelpMethods.Msg(ex.Message.ToString()); } }
private async void ColorFrameReader_FrameArrivedAsync(MediaFrameReader sender, MediaFrameArrivedEventArgs args) { if (_skippedFrames < _skipFrameCount) { _skippedFrames++; return; } _skippedFrames = 0; var mediaFrameReference = sender.TryAcquireLatestFrame(); var videoMediaFrame = mediaFrameReference?.VideoMediaFrame; var softwareBitmap = videoMediaFrame?.SoftwareBitmap; if (softwareBitmap != null) { var encoderId = BitmapEncoder.JpegEncoderId; InMemoryRandomAccessStream jpegStream = new InMemoryRandomAccessStream(); var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue(_imageQuality, PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); BitmapEncoder bitmapEncoder = await BitmapEncoder.CreateAsync(BitmapEncoder.JpegEncoderId, jpegStream, propertySet); bitmapEncoder.BitmapTransform.Rotation = IntToBitmapRotation(_videoRotation); bitmapEncoder.SetSoftwareBitmap(softwareBitmap); await bitmapEncoder.FlushAsync(); if (_activityCounter++ > 50) { Debug.WriteLine("."); _activityCounter = 0; } else { Debug.Write("."); } Interlocked.Exchange(ref _jpegStreamBuffer, jpegStream); if (_previewVideoEnabled) { // Changes to XAML ImageElement must happen on UI thread through Dispatcher var task = imageElement.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, async() => { // Don't let two copies of this task run at the same time. if (taskRunning) { return; } taskRunning = true; try { InMemoryRandomAccessStream imageElementJpegStream = _jpegStreamBuffer; if (imageElementJpegStream != null) { BitmapImage bitmapImage = new BitmapImage(); await bitmapImage.SetSourceAsync(imageElementJpegStream); imageElement.Source = bitmapImage; } } catch (Exception imageElementException) { Debug.WriteLine("Image Element writing exception. " + imageElementException.Message); } taskRunning = false; }); } } if (mediaFrameReference != null) { mediaFrameReference.Dispose(); } }
/// <summary> /// Applies the user-provided scale and rotation operation to the original image file. /// The "Transcoding" mode is used which preserves image metadata and performs other /// optimizations when possible. /// /// This method attempts to perform "soft" rotation using the EXIF orientation flag when possible, /// but falls back to a hard rotation of the image pixels. /// </summary> private async void Save_Click(object sender, RoutedEventArgs e) { try { rootPage.NotifyUser("Saving file...", NotifyType.StatusMessage); // Create a new encoder and initialize it with data from the original file. // The encoder writes to an in-memory stream, we then copy the contents to the file. // This allows the application to perform in-place editing of the file: any unedited data // is copied to the destination, and the original file is overwritten // with updated data. StorageFile file = await m_futureAccess.GetFileAsync(m_fileToken); using (IRandomAccessStream fileStream = await file.OpenAsync(FileAccessMode.ReadWrite), memStream = new InMemoryRandomAccessStream()) { BitmapDecoder decoder = await BitmapDecoder.CreateAsync(fileStream); // Use the native (no orientation applied) image dimensions because we want to handle // orientation ourselves. uint originalWidth = decoder.PixelWidth; uint originalHeight = decoder.PixelHeight; // Set the encoder's destination to the temporary, in-memory stream. BitmapEncoder encoder = await BitmapEncoder.CreateForTranscodingAsync(memStream, decoder); // Scaling occurs before flip/rotation, therefore use the original dimensions // (no orientation applied) as parameters for scaling. // Dimensions are rounded down by BitmapEncoder to the nearest integer. if (m_scaleFactor != 1.0) { encoder.BitmapTransform.ScaledWidth = (uint)(originalWidth * m_scaleFactor); encoder.BitmapTransform.ScaledHeight = (uint)(originalHeight * m_scaleFactor); } // If the file format supports EXIF orientation ("System.Photo.Orientation") then // update the orientation flag to reflect any user-specified rotation. // Otherwise, perform a hard rotate using BitmapTransform. if (m_disableExifOrientation == false) { BitmapPropertySet properties = new BitmapPropertySet(); ushort netExifOrientation = Helpers.ConvertToExifOrientationFlag( Helpers.AddPhotoOrientation(m_userRotation, m_exifOrientation) ); // BitmapProperties requires the application to explicitly declare the type // of the property to be written - this is different from FileProperties which // automatically coerces the value to the correct type. System.Photo.Orientation // is defined as an unsigned 16 bit integer. BitmapTypedValue orientationTypedValue = new BitmapTypedValue( netExifOrientation, Windows.Foundation.PropertyType.UInt16 ); properties.Add("System.Photo.Orientation", orientationTypedValue); await encoder.BitmapProperties.SetPropertiesAsync(properties); } else { encoder.BitmapTransform.Rotation = Helpers.ConvertToBitmapRotation(m_userRotation); } // Attempt to generate a new thumbnail to reflect any rotation operation. encoder.IsThumbnailGenerated = true; try { await encoder.FlushAsync(); } catch (Exception err) { switch (err.HResult) { case WINCODEC_ERR_UNSUPPORTEDOPERATION: // If the encoder does not support writing a thumbnail, then try again // but disable thumbnail generation. encoder.IsThumbnailGenerated = false; break; default: throw err; } } if (encoder.IsThumbnailGenerated == false) { await encoder.FlushAsync(); } // Now that the file has been written to the temporary stream, copy the data to the file. memStream.Seek(0); fileStream.Seek(0); fileStream.Size = 0; await RandomAccessStream.CopyAsync(memStream, fileStream); // Because the original file has been overwritten, reload it in the UI. ResetSessionState(); await DisplayImageFileAsync(file); rootPage.NotifyUser("Successfully saved file: " + file.Name, NotifyType.StatusMessage); } } catch (Exception err) { if (err.HResult == WINCODEC_ERR_COMPONENTNOTFOUND) { // Some image formats (e.g. ICO) do not have encoders. rootPage.NotifyUser("Error: this file format may not support editing.", NotifyType.ErrorMessage); } else { rootPage.NotifyUser("Error: " + err.Message, NotifyType.ErrorMessage); } ResetPersistedState(); ResetSessionState(); } }
async Task <byte[]> GetImageAsByteAsync(Guid format, int quality, int desiredWidth, int desiredHeight) { if (Control == null || Control.Source == null) { return(null); } var bitmap = Control.Source as WriteableBitmap; if (bitmap == null) { return(null); } byte[] pixels = null; uint pixelsWidth = (uint)bitmap.PixelWidth; uint pixelsHeight = (uint)bitmap.PixelHeight; if (desiredWidth != 0 || desiredHeight != 0) { double widthRatio = (double)desiredWidth / (double)bitmap.PixelWidth; double heightRatio = (double)desiredHeight / (double)bitmap.PixelHeight; double scaleRatio = Math.Min(widthRatio, heightRatio); if (desiredWidth == 0) { scaleRatio = heightRatio; } if (desiredHeight == 0) { scaleRatio = widthRatio; } uint aspectWidth = (uint)((double)bitmap.PixelWidth * scaleRatio); uint aspectHeight = (uint)((double)bitmap.PixelHeight * scaleRatio); using (var tempStream = new InMemoryRandomAccessStream()) { byte[] tempPixels = await GetBytesFromBitmapAsync(bitmap); var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.PngEncoderId, tempStream); encoder.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Premultiplied, pixelsWidth, pixelsHeight, 96, 96, tempPixels); await encoder.FlushAsync(); tempStream.Seek(0); BitmapDecoder decoder = await BitmapDecoder.CreateAsync(tempStream); BitmapTransform transform = new BitmapTransform() { ScaledWidth = aspectWidth, ScaledHeight = aspectHeight, InterpolationMode = BitmapInterpolationMode.Cubic }; PixelDataProvider pixelData = await decoder.GetPixelDataAsync( BitmapPixelFormat.Bgra8, BitmapAlphaMode.Premultiplied, transform, ExifOrientationMode.RespectExifOrientation, ColorManagementMode.DoNotColorManage); pixels = pixelData.DetachPixelData(); pixelsWidth = aspectWidth; pixelsHeight = aspectHeight; } } else { pixels = await GetBytesFromBitmapAsync(bitmap); } using (var stream = new InMemoryRandomAccessStream()) { BitmapEncoder encoder; if (format == BitmapEncoder.JpegEncoderId) { var propertySet = new BitmapPropertySet(); var qualityValue = new BitmapTypedValue((double)quality / 100d, Windows.Foundation.PropertyType.Single); propertySet.Add("ImageQuality", qualityValue); encoder = await BitmapEncoder.CreateAsync(format, stream, propertySet); } else { encoder = await BitmapEncoder.CreateAsync(format, stream); } encoder.SetPixelData(BitmapPixelFormat.Bgra8, BitmapAlphaMode.Premultiplied, pixelsWidth, pixelsHeight, 96, 96, pixels); await encoder.FlushAsync(); stream.Seek(0); var bytes = new byte[stream.Size]; await stream.ReadAsync(bytes.AsBuffer(), (uint)stream.Size, InputStreamOptions.None); return(bytes); } }
public async Task Initialize(VideoSetting videoSetting) { await CoreApplication.MainView.CoreWindow.Dispatcher.RunAndAwaitAsync(CoreDispatcherPriority.Normal, async() => { _threadsCount = videoSetting.UsedThreads; _stoppedThreads = videoSetting.UsedThreads; _lastFrameAdded.Start(); _imageQuality = new BitmapPropertySet(); var imageQualityValue = new BitmapTypedValue(videoSetting.VideoQuality, Windows.Foundation.PropertyType.Single); _imageQuality.Add("ImageQuality", imageQualityValue); _mediaCapture = new MediaCapture(); var frameSourceGroups = await MediaFrameSourceGroup.FindAllAsync(); var sourceGroups = frameSourceGroups.Select(g => new { Group = g, SourceInfo = g.SourceInfos.FirstOrDefault(i => i.SourceKind == MediaFrameSourceKind.Color) }).Where(g => g.SourceInfo != null).ToList(); var settings = new MediaCaptureInitializationSettings() { SourceGroup = sourceGroups?.FirstOrDefault()?.Group, SharingMode = MediaCaptureSharingMode.ExclusiveControl, //With CPU the results contain always SoftwareBitmaps, otherwise with GPU //they preferring D3DSurface MemoryPreference = MediaCaptureMemoryPreference.Cpu, //Capture only video, no audio StreamingCaptureMode = StreamingCaptureMode.Video }; await _mediaCapture.InitializeAsync(settings); var mediaFrameSource = this._mediaCapture.FrameSources[sourceGroups?.FirstOrDefault()?.SourceInfo.Id]; /* * // Commented to reduce CPU usage. * var videoDeviceController = mediaFrameSource.Controller.VideoDeviceController; * * videoDeviceController.DesiredOptimization = Windows.Media.Devices.MediaCaptureOptimization.Quality; * videoDeviceController.PrimaryUse = Windows.Media.Devices.CaptureUse.Video; * * //Set exposure (auto light adjustment) * if (_mediaCapture.VideoDeviceController.Exposure.Capabilities.Supported * && _mediaCapture.VideoDeviceController.Exposure.Capabilities.AutoModeSupported) * { * _mediaCapture.VideoDeviceController.Exposure.TrySetAuto(true); * } * * var videoResolutionWidthHeight = VideoResolutionWidthHeight.Get(videoSetting.VideoResolution); * var videoSubType = VideoSubtypeHelper.Get(videoSetting.VideoSubtype); * * //Set resolution, frame rate and video subtyp * var videoFormat = mediaFrameSource.SupportedFormats.Where(sf => sf.VideoFormat.Width == videoResolutionWidthHeight.Width * && sf.VideoFormat.Height == videoResolutionWidthHeight.Height * && sf.Subtype == videoSubType) * .OrderByDescending(m => m.FrameRate.Numerator / m.FrameRate.Denominator) * .First(); * * await mediaFrameSource.SetFormatAsync(videoFormat); */ _mediaFrameReader = await _mediaCapture.CreateFrameReaderAsync(mediaFrameSource); await _mediaFrameReader.StartAsync(); }); }
public static async void SaveAsync(StorageFile file, SoftwareBitmap bitmap) { CachedFileManager.DeferUpdates(file); using (var filestream = await file.OpenAsync(FileAccessMode.ReadWrite)) { Guid type; var propertySet = new BitmapPropertySet(); BitmapEncoder encoder = null; // write to file switch (file.FileType.ToLower()) { case ".jxr": type = BitmapEncoder.JpegXREncoderId; break; case ".jpg": case ".jpeg": type = BitmapEncoder.JpegEncoderId; break; case ".png": type = BitmapEncoder.PngEncoderId; break; case ".bmp": type = BitmapEncoder.BmpEncoderId; break; case ".tiff": case ".tif": var compressionValue = new BitmapTypedValue( TiffCompressionMode.None, // no compression PropertyType.UInt8 ); propertySet.Add("TiffCompressionMethod", compressionValue); type = BitmapEncoder.TiffEncoderId; break; default: throw new FormatException("Format not supported: " + file.FileType); } encoder = await BitmapEncoder.CreateAsync(type, filestream, propertySet); //Needs to run in the UI thread because f**k performance await CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () => { //Do some UI-code that must be run on the UI thread. encoder.SetSoftwareBitmap(bitmap); }); await encoder.FlushAsync(); encoder = null; bitmap.Dispose(); // Let Windows know that we're finished changing the file so // the other app can update the remote version of the file. // Completing updates may require Windows to ask for user input. FileUpdateStatus status = await CachedFileManager.CompleteUpdatesAsync(file); if (status != FileUpdateStatus.Complete && status != FileUpdateStatus.CompleteAndRenamed) { throw new IOException("File could not be saved"); } } }