Browse Source

Stub out approach

pull/1861/head
James Jackson-South 5 years ago
parent
commit
61c30de89e
  1. 17
      src/ImageSharp/Formats/Png/PngDecoder.cs
  2. 42
      src/ImageSharp/Formats/Png/PngDecoderCore.cs

17
src/ImageSharp/Formats/Png/PngDecoder.cs

@ -20,12 +20,25 @@ namespace SixLabors.ImageSharp.Formats.Png
public Image<TPixel> Decode<TPixel>(Configuration configuration, Stream stream) public Image<TPixel> Decode<TPixel>(Configuration configuration, Stream stream)
where TPixel : unmanaged, IPixel<TPixel> where TPixel : unmanaged, IPixel<TPixel>
{ {
var decoder = new PngDecoderCore(configuration, this); PngDecoderCore decoder = new(configuration, this);
return decoder.Decode<TPixel>(configuration, stream); return decoder.Decode<TPixel>(configuration, stream);
} }
/// <inheritdoc /> /// <inheritdoc />
public Image Decode(Configuration configuration, Stream stream) => this.Decode<Rgba32>(configuration, stream); public Image Decode(Configuration configuration, Stream stream)
{
PngDecoderCore decoder = new(configuration, true);
IImageInfo info = decoder.Identify(configuration, stream);
stream.Position = 0;
switch (info.Metadata.GetPngMetadata().ColorType)
{
default:
break;
}
return this.Decode<Rgba32>(configuration, stream);
}
/// <inheritdoc/> /// <inheritdoc/>
public Task<Image<TPixel>> DecodeAsync<TPixel>(Configuration configuration, Stream stream, CancellationToken cancellationToken) public Task<Image<TPixel>> DecodeAsync<TPixel>(Configuration configuration, Stream stream, CancellationToken cancellationToken)

42
src/ImageSharp/Formats/Png/PngDecoderCore.cs

@ -124,6 +124,13 @@ namespace SixLabors.ImageSharp.Formats.Png
this.ignoreMetadata = options.IgnoreMetadata; this.ignoreMetadata = options.IgnoreMetadata;
} }
internal PngDecoderCore(Configuration configuration, bool ignoreMetadata)
{
this.Configuration = configuration ?? Configuration.Default;
this.memoryAllocator = this.Configuration.MemoryAllocator;
this.ignoreMetadata = ignoreMetadata;
}
/// <inheritdoc/> /// <inheritdoc/>
public Configuration Configuration { get; } public Configuration Configuration { get; }
@ -168,12 +175,12 @@ namespace SixLabors.ImageSharp.Formats.Png
break; break;
case PngChunkType.Palette: case PngChunkType.Palette:
var pal = new byte[chunk.Length]; byte[] pal = new byte[chunk.Length];
chunk.Data.GetSpan().CopyTo(pal); chunk.Data.GetSpan().CopyTo(pal);
this.palette = pal; this.palette = pal;
break; break;
case PngChunkType.Transparency: case PngChunkType.Transparency:
var alpha = new byte[chunk.Length]; byte[] alpha = new byte[chunk.Length];
chunk.Data.GetSpan().CopyTo(alpha); chunk.Data.GetSpan().CopyTo(alpha);
this.paletteAlpha = alpha; this.paletteAlpha = alpha;
this.AssignTransparentMarkers(alpha, pngMetadata); this.AssignTransparentMarkers(alpha, pngMetadata);
@ -190,7 +197,7 @@ namespace SixLabors.ImageSharp.Formats.Png
case PngChunkType.Exif: case PngChunkType.Exif:
if (!this.ignoreMetadata) if (!this.ignoreMetadata)
{ {
var exifData = new byte[chunk.Length]; byte[] exifData = new byte[chunk.Length];
chunk.Data.GetSpan().CopyTo(exifData); chunk.Data.GetSpan().CopyTo(exifData);
metadata.ExifProfile = new ExifProfile(exifData); metadata.ExifProfile = new ExifProfile(exifData);
} }
@ -263,7 +270,7 @@ namespace SixLabors.ImageSharp.Formats.Png
case PngChunkType.Exif: case PngChunkType.Exif:
if (!this.ignoreMetadata) if (!this.ignoreMetadata)
{ {
var exifData = new byte[chunk.Length]; byte[] exifData = new byte[chunk.Length];
chunk.Data.GetSpan().CopyTo(exifData); chunk.Data.GetSpan().CopyTo(exifData);
metadata.ExifProfile = new ExifProfile(exifData); metadata.ExifProfile = new ExifProfile(exifData);
} }
@ -364,11 +371,10 @@ namespace SixLabors.ImageSharp.Formats.Png
/// <param name="pngMetadata">The metadata to read to.</param> /// <param name="pngMetadata">The metadata to read to.</param>
/// <param name="data">The data containing physical data.</param> /// <param name="data">The data containing physical data.</param>
private void ReadGammaChunk(PngMetadata pngMetadata, ReadOnlySpan<byte> data) private void ReadGammaChunk(PngMetadata pngMetadata, ReadOnlySpan<byte> data)
{
// The value is encoded as a 4-byte unsigned integer, representing gamma times 100000. // The value is encoded as a 4-byte unsigned integer, representing gamma times 100000.
// For example, a gamma of 1/2.2 would be stored as 45455. // For example, a gamma of 1/2.2 would be stored as 45455.
pngMetadata.Gamma = BinaryPrimitives.ReadUInt32BigEndian(data) / 100_000F; => pngMetadata.Gamma = BinaryPrimitives.ReadUInt32BigEndian(data) / 100_000F;
}
/// <summary> /// <summary>
/// Initializes the image and various buffers needed for processing /// Initializes the image and various buffers needed for processing
@ -477,19 +483,17 @@ namespace SixLabors.ImageSharp.Formats.Png
private void ReadScanlines<TPixel>(PngChunk chunk, ImageFrame<TPixel> image, PngMetadata pngMetadata) private void ReadScanlines<TPixel>(PngChunk chunk, ImageFrame<TPixel> image, PngMetadata pngMetadata)
where TPixel : unmanaged, IPixel<TPixel> where TPixel : unmanaged, IPixel<TPixel>
{ {
using (var deframeStream = new ZlibInflateStream(this.currentStream, this.ReadNextDataChunk)) using var deframeStream = new ZlibInflateStream(this.currentStream, this.ReadNextDataChunk);
{ deframeStream.AllocateNewBytes(chunk.Length, true);
deframeStream.AllocateNewBytes(chunk.Length, true); DeflateStream dataStream = deframeStream.CompressedStream;
DeflateStream dataStream = deframeStream.CompressedStream;
if (this.header.InterlaceMethod == PngInterlaceMode.Adam7) if (this.header.InterlaceMethod == PngInterlaceMode.Adam7)
{ {
this.DecodeInterlacedPixelData(dataStream, image, pngMetadata); this.DecodeInterlacedPixelData(dataStream, image, pngMetadata);
} }
else else
{ {
this.DecodePixelData(dataStream, image, pngMetadata); this.DecodePixelData(dataStream, image, pngMetadata);
}
} }
} }

Loading…
Cancel
Save