public static Bgra32ImageBuffer ReadImageBuffer(this OpenSlideImage image, int level, long x, long y, long w, long h) { var buffer = new Bgra32ImageBuffer(checked ((int)w), checked ((int)h)); image.ReadRegion(level, x, y, w, h, ref buffer.GetPinnableReference()); return(buffer); }
public static void GetThumbnailAsJpegToStream(this OpenSlideImage image, int maxSize, Stream stream, int quality = 75) { using (var thumbnail = GenerateThumbnail(image, maxSize, maxSize)) { byte[] buffer = ArrayPool <byte> .Shared.Rent(EnsureMinimumSize(maxSize *maxSize * 4 * 2)); try { using (var ms = new MemoryStream(buffer)) { thumbnail.SaveAsJpeg(ms, new JpegEncoder() { Quality = quality }); ms.SetLength(ms.Position); ms.Position = 0; ms.CopyTo(stream); } } finally { ArrayPool <byte> .Shared.Return(buffer); } } }
public static void GetThumbnailAsJpegToStream(this OpenSlideImage image, int maxSize, MemoryStream stream, int quality = 75) { using var thumbnail = GenerateThumbnail(image, maxSize, maxSize); thumbnail.SaveAsJpeg(stream, new JpegEncoder { Quality = quality }); }
public static void GetAssociatedImageAsJpegToStream(this OpenSlideImage image, string name, MemoryStream stream) { using (var img = WriteImage(image, name)) { img.SaveAsJpeg(stream, new JpegEncoder()); } }
public static async Task GetAssociatedImageAsJpegToStreamAsync(this OpenSlideImage image, string name, Stream stream, int quality = 75) { using (var img = WriteImage(image, name)) { byte[] buffer = ArrayPool <byte> .Shared.Rent(EnsureMinimumSize(img.Width *img.Height * 4 * 2)); try { using (var ms = new MemoryStream(buffer)) { img.SaveAsJpeg(ms, new JpegEncoder() { Quality = quality }); ms.SetLength(ms.Position); ms.Position = 0; await ms.CopyToAsync(stream).ConfigureAwait(false); } } finally { ArrayPool <byte> .Shared.Return(buffer); } } }
public static Bgra32ImageBuffer ReadAssociatedImageBuffer(this OpenSlideImage image, string name, long w, long h) { var buffer = new Bgra32ImageBuffer(checked ((int)w), checked ((int)h)); image.ReadAssociatedImage(name, ref buffer.GetPinnableReference()); return(buffer); }
private static Bgra32ImageBuffer ReadImage(OpenSlideImage image, string name) { if (!image.TryGetAssociatedImageDimensions(name, out var dims)) { throw new KeyNotFoundException(); } return(image.ReadAssociatedImageBuffer(name, dims.Width, dims.Height)); }
public static void GetAssociatedImageAsJpegToStream(this OpenSlideImage image, string name, MemoryStream stream, int quality = 75) { using var buffer = ReadImage(image, name); using var ms = PooledMemoryStreamManager.Shared.GetStream(); buffer.GetImage().SaveAsJpeg(stream, new JpegEncoder { Quality = quality }); }
public static byte[] GetThumbnailAsJpeg(this OpenSlideImage image, int maxSize, int quality = 75) { using var thumbnail = GenerateThumbnail(image, maxSize, maxSize); using var ms = PooledMemoryStreamManager.Shared.GetStream(); thumbnail.SaveAsJpeg(ms, new JpegEncoder { Quality = quality }); return(ms.ToArray()); }
public static byte[] GetAssociatedImageAsJpeg(this OpenSlideImage image, string name, int quality = 75) { using var buffer = ReadImage(image, name); using var ms = PooledMemoryStreamManager.Shared.GetStream(); buffer.GetImage().SaveAsJpeg(ms, new JpegEncoder { Quality = quality }); return(ms.ToArray()); }
public static async Task GetAssociatedImageAsJpegToStreamAsync(this OpenSlideImage image, string name, Stream stream, int quality = 75, CancellationToken cancellationToken = default) { using var buffer = ReadImage(image, name); using var ms = PooledMemoryStreamManager.Shared.GetStream(); buffer.GetImage().SaveAsJpeg(ms, new JpegEncoder { Quality = quality }); ms.Seek(0, SeekOrigin.Begin); await ms.CopyToAsync(stream, 4096, cancellationToken).ConfigureAwait(false); }
public static void GetThumbnailAsJpegToStream(this OpenSlideImage image, int maxSize, Stream stream, int quality = 75) { using var thumbnail = GenerateThumbnail(image, maxSize, maxSize); using var ms = PooledMemoryStreamManager.Shared.GetStream(); thumbnail.SaveAsJpeg(ms, new JpegEncoder { Quality = quality }); ms.Seek(0, SeekOrigin.Begin); ms.CopyTo(stream); }
public static async Task GetThumbnailAsJpegToStreamAsync(this OpenSlideImage image, int maxSize, Stream stream, int quality = 75, CancellationToken cancellationToken = default) { using var thumbnail = GenerateThumbnail(image, maxSize, maxSize); using var ms = PooledMemoryStreamManager.Shared.GetStream(); thumbnail.SaveAsJpeg(ms, new JpegEncoder { Quality = quality }); ms.Seek(0, SeekOrigin.Begin); await ms.CopyToAsync(stream, 4096, cancellationToken).ConfigureAwait(false); }
private static Image <Bgra32> WriteImage(OpenSlideImage image, string name) { if (!image.TryGetAssociatedImageDimensions(name, out var dims)) { throw new KeyNotFoundException(); } var dest = new Image <Bgra32>((int)dims.Width, (int)dims.Height); image.ReadAssociatedImage(name, ref Unsafe.As <Bgra32, byte>(ref MemoryMarshal.GetReference(dest.GetPixelSpan()))); return(dest); }
private static Image <Bgra32> WriteImage(OpenSlideImage image, string name) { if (!image.TryGetAssociatedImageDimensions(name, out var dims)) { throw new KeyNotFoundException(); } var dest = new Image <Bgra32>((int)dims.Width, (int)dims.Height); var frame = dest.Frames.RootFrame; image.DangerousReadAssociatedImage(name, ref Unsafe.As <Bgra32, byte>(ref frame.DangerousGetPinnableReferenceToPixelBuffer())); return(dest); }
private static Image <Bgra32> GenerateThumbnail(OpenSlideImage image, int maxWidth, int maxHeight) { if (image == null) { throw new ArgumentNullException(nameof(image)); } (long width, long height) = image.Dimensions; // 决定合适的level double downsampleWidth = width / (double)maxWidth; double downsampleHeight = height / (double)maxHeight; double downsample = Math.Max(downsampleWidth, downsampleHeight); int level = image.GetBestLevelForDownsample(downsample); (long levelWidth, long levelHeight) = image.GetLevelDimensions(level); // 计算目标大小 int targetWidth, targetHeight; if (downsampleWidth > downsampleHeight) { // width缩小较大,将maxWidth作为标准 targetWidth = maxWidth; targetHeight = (int)(height / downsampleWidth); } else { // height缩小较大,将maxHeight作为标准 targetWidth = (int)(width / downsampleHeight); targetHeight = maxHeight; } Image <Bgra32> output; checked { output = new Image <Bgra32>((int)levelWidth, (int)levelHeight); } output.Mutate(ctx => { ctx.Apply(img => { var frame = img.Frames.RootFrame; image.DangerousReadRegion( level, 0, 0, levelWidth, levelHeight, ref Unsafe.As <Bgra32, byte>(ref frame.DangerousGetPinnableReferenceToPixelBuffer())); }); ctx.Resize(targetWidth, targetHeight); }); return(output); }
/// <summary> /// Read the property with the specified <paramref name="name"/>. If the property does not exists, This function returns <paramref name="defaultValue"/>. /// </summary> /// <param name="image">The <see cref="OpenSlideImage"/> object.</param> /// <param name="name">The property name.</param> /// <param name="defaultValue">The value returned when the specified property does not exists.</param> /// <returns>The value of the property or <paramref name="defaultValue"/>.</returns> public static string?GetProperty(this OpenSlideImage image, string name, string?defaultValue) { if (image == null) { throw new ArgumentNullException(nameof(image)); } if (!image.TryGetProperty(name, out string?value)) { return(defaultValue); } return(value); }
/// <summary> /// Initialize a <see cref="DeepZoomGenerator"/> instance with the specified parameters. /// </summary> /// <param name="image">The OpenSlide image.</param> /// <param name="tileSize">The tile size paramter.</param> /// <param name="overlap">The overlap paramter.</param> /// <param name="limitBounds">Whether image bounds should be respected.</param> /// <param name="disposeImage">Whether the OpenSlide image instance should be disposed when this <see cref="DeepZoomGenerator"/> instance is disposed.</param> public DeepZoomGenerator(OpenSlideImage image, int tileSize = 254, int overlap = 1, bool limitBounds = true, bool disposeImage = false) { _image = image ?? throw new ArgumentNullException(nameof(image)); _disposeImage = disposeImage; long width, height; if (limitBounds) { _boundX = image.BoundsX ?? 0; _boundY = image.BoundsY ?? 0; _width = width = image.BoundsWidth ?? image.Width; _height = height = image.BoundsHeight ?? image.Height; } else { _boundX = 0; _boundY = 0; _width = width = image.Width; _height = height = image.Height; } DeepZoomLayer[] dzLayers = DeepZoomHelper.CalculateDeepZoomLayers(width, height); DeepZoomLayerInformation[] layers = new DeepZoomLayerInformation[dzLayers.Length]; for (int i = 0; i < layers.Length; i++) { DeepZoomLayer dzLayer = dzLayers[i]; int layerDownsample = 1 << (dzLayers.Length - i - 1); int level = image.GetBestLevelForDownsample(layerDownsample); (long levelWidth, long levelHeight) = image.GetLevelDimensions(level); layers[i] = new DeepZoomLayerInformation { Level = level, LevelDownsample = image.GetLevelDownsample(level), LevelWidth = levelWidth, LevelHeight = levelHeight, LayerDownsample = layerDownsample, LayerWidth = dzLayer.Width, LayerHeight = dzLayer.Height }; } _layers = layers; _tileSize = tileSize; _overlap = overlap; }
public static void GetThumbnailAsJpegToStream(this OpenSlideImage image, int maxSize, MemoryStream stream) { using (var thumbnail = GenerateThumbnail(image, maxSize, maxSize)) { byte[] buffer = ArrayPool <byte> .Shared.Rent(EnsureMinimumSize(maxSize *maxSize * 4 * 2)); try { thumbnail.SaveAsJpeg(stream, new JpegEncoder()); } finally { ArrayPool <byte> .Shared.Return(buffer); } } }
/// <summary> /// Read the property with the specified <paramref name="name"/> and parse it as a <see cref="int"/> value. If the property does not exists or can not be parsed as <see cref="int"/>, This function returns <paramref name="defaultValue"/>. /// </summary> /// <param name="image">The <see cref="OpenSlideImage"/> object.</param> /// <param name="name">The property name.</param> /// <param name="defaultValue">The default value.</param> /// <returns>The value of the property or <paramref name="defaultValue"/>.</returns> public static int GetProperty(this OpenSlideImage image, string name, int defaultValue) { if (image == null) { throw new ArgumentNullException(nameof(image)); } if (!image.TryGetProperty(name, out string?value)) { return(defaultValue); } if (!int.TryParse(value, out var result)) { return(defaultValue); } return(result); }
public static byte[] GetAssociatedImageAsJpeg(this OpenSlideImage image, string name) { using (var img = WriteImage(image, name)) { byte[] buffer = ArrayPool <byte> .Shared.Rent(EnsureMinimumSize(img.Width *img.Height * 4 * 2)); try { using (var ms = new MemoryStream(buffer)) { img.SaveAsJpeg(ms, new JpegEncoder()); ms.SetLength(ms.Position); return(ms.ToArray()); } } finally { ArrayPool <byte> .Shared.Return(buffer); } } }
public static byte[] GetThumbnailAsJpeg(this OpenSlideImage image, int maxSize) { using (var thumbnail = GenerateThumbnail(image, maxSize, maxSize)) { byte[] buffer = ArrayPool <byte> .Shared.Rent(EnsureMinimumSize(maxSize *maxSize * 4 * 2)); try { using (var ms = new MemoryStream(buffer)) { thumbnail.SaveAsJpeg(ms, new JpegEncoder()); ms.SetLength(ms.Position); return(ms.ToArray()); } } finally { ArrayPool <byte> .Shared.Return(buffer); } } }
public static async Task GetThumbnailAsJpegToStreamAsync(this OpenSlideImage image, int maxSize, Stream stream) { using (var thumbnail = GenerateThumbnail(image, maxSize, maxSize)) { byte[] buffer = ArrayPool <byte> .Shared.Rent(EnsureMinimumSize(maxSize *maxSize * 4 * 2)); try { using (var ms = new MemoryStream(buffer)) { thumbnail.SaveAsJpeg(ms, new JpegEncoder()); ms.SetLength(ms.Position); ms.Position = 0; await ms.CopyToAsync(stream).ConfigureAwait(false); } } finally { ArrayPool <byte> .Shared.Return(buffer); } } }
private static Image <Bgra32> GenerateThumbnail(OpenSlideImage image, int maxWidth, int maxHeight) { if (image == null) { throw new ArgumentNullException(nameof(image)); } (long width, long height) = image.Dimensions; // Find the appropriate level double downsampleWidth = width / (double)maxWidth; double downsampleHeight = height / (double)maxHeight; double downsample = Math.Max(downsampleWidth, downsampleHeight); int level = image.GetBestLevelForDownsample(downsample); (long levelWidth, long levelHeight) = image.GetLevelDimensions(level); // Calculate target size int targetWidth, targetHeight; if (downsampleWidth > downsampleHeight) { targetWidth = maxWidth; targetHeight = (int)(height / downsampleWidth); } else { targetWidth = (int)(width / downsampleHeight); targetHeight = maxHeight; } using Bgra32ImageBuffer buffer = image.ReadImageBuffer(level, 0, 0, levelWidth, levelHeight); return(buffer.GetImage().Clone(ctx => { ctx.Resize(targetWidth, targetHeight); })); }