Browse Source

Merge remote-tracking branch 'origin/master' into bp/tiff24bit

# Conflicts:
#	src/ImageSharp/Formats/Tiff/PhotometricInterpretation/BlackIsZero16TiffColor{TPixel}.cs
#	src/ImageSharp/Formats/Tiff/PhotometricInterpretation/Rgb161616TiffColor{TPixel}.cs
pull/1724/head
Brian Popow 5 years ago
parent
commit
51e18702d9
  1. 22
      src/ImageSharp/Formats/Tiff/PhotometricInterpretation/BlackIsZero16TiffColor{TPixel}.cs
  2. 21
      src/ImageSharp/Formats/Tiff/PhotometricInterpretation/BlackIsZero8TiffColor{TPixel}.cs
  3. 26
      src/ImageSharp/Formats/Tiff/PhotometricInterpretation/Rgb161616TiffColor{TPixel}.cs
  4. 28
      src/ImageSharp/Formats/Tiff/PhotometricInterpretation/Rgb888TiffColor{TPixel}.cs
  5. 10
      src/ImageSharp/Formats/Tiff/PhotometricInterpretation/TiffColorDecoderFactory{TPixel}.cs
  6. 2
      src/ImageSharp/Formats/Tiff/TiffDecoderCore.cs
  7. 2
      tests/ImageSharp.Tests/Formats/Tiff/PhotometricInterpretation/BlackIsZeroTiffColorTests.cs
  8. 2
      tests/ImageSharp.Tests/Formats/Tiff/PhotometricInterpretation/RgbTiffColorTests.cs

22
src/ImageSharp/Formats/Tiff/PhotometricInterpretation/BlackIsZero16TiffColor{TPixel}.cs

@ -16,11 +16,18 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
{ {
private readonly bool isBigEndian; private readonly bool isBigEndian;
private readonly Configuration configuration;
/// <summary> /// <summary>
/// Initializes a new instance of the <see cref="BlackIsZero16TiffColor{TPixel}" /> class. /// Initializes a new instance of the <see cref="BlackIsZero16TiffColor{TPixel}" /> class.
/// </summary> /// </summary>
/// <param name="configuration">The configuration.</param>
/// <param name="isBigEndian">if set to <c>true</c> decodes the pixel data as big endian, otherwise as little endian.</param> /// <param name="isBigEndian">if set to <c>true</c> decodes the pixel data as big endian, otherwise as little endian.</param>
public BlackIsZero16TiffColor(bool isBigEndian) => this.isBigEndian = isBigEndian; public BlackIsZero16TiffColor(Configuration configuration, bool isBigEndian)
{
this.configuration = configuration;
this.isBigEndian = isBigEndian;
}
/// <inheritdoc/> /// <inheritdoc/>
public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height) public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height)
@ -47,13 +54,14 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
} }
else else
{ {
for (int x = 0; x < pixelRow.Length; x++) int byteCount = pixelRow.Length * 2;
{ PixelOperations<TPixel>.Instance.FromL16Bytes(
ushort intensity = TiffUtils.ConvertToUShortLittleEndian(data.Slice(offset, 2)); this.configuration,
offset += 2; data.Slice(offset, byteCount),
pixelRow,
pixelRow.Length);
pixelRow[x] = TiffUtils.ColorFromL16(l16, intensity, color); offset += byteCount;
}
} }
} }
} }

21
src/ImageSharp/Formats/Tiff/PhotometricInterpretation/BlackIsZero8TiffColor{TPixel}.cs

@ -2,7 +2,6 @@
// Licensed under the Apache License, Version 2.0. // Licensed under the Apache License, Version 2.0.
using System; using System;
using SixLabors.ImageSharp.Formats.Tiff.Utils;
using SixLabors.ImageSharp.Memory; using SixLabors.ImageSharp.Memory;
using SixLabors.ImageSharp.PixelFormats; using SixLabors.ImageSharp.PixelFormats;
@ -14,22 +13,26 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
internal class BlackIsZero8TiffColor<TPixel> : TiffBaseColorDecoder<TPixel> internal class BlackIsZero8TiffColor<TPixel> : TiffBaseColorDecoder<TPixel>
where TPixel : unmanaged, IPixel<TPixel> where TPixel : unmanaged, IPixel<TPixel>
{ {
private readonly Configuration configuration;
public BlackIsZero8TiffColor(Configuration configuration) => this.configuration = configuration;
/// <inheritdoc/> /// <inheritdoc/>
public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height) public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height)
{ {
var color = default(TPixel);
int offset = 0; int offset = 0;
var l8 = default(L8);
for (int y = top; y < top + height; y++) for (int y = top; y < top + height; y++)
{ {
Span<TPixel> pixelRow = pixels.GetRowSpan(y).Slice(left, width); Span<TPixel> pixelRow = pixels.GetRowSpan(y).Slice(left, width);
for (int x = 0; x < pixelRow.Length; x++) int byteCount = pixelRow.Length;
{ PixelOperations<TPixel>.Instance.FromL8Bytes(
byte intensity = data[offset++]; this.configuration,
pixelRow[x] = TiffUtils.ColorFromL8(l8, intensity, color); data.Slice(offset, byteCount),
} pixelRow,
pixelRow.Length);
offset += byteCount;
} }
} }
} }

26
src/ImageSharp/Formats/Tiff/PhotometricInterpretation/Rgb161616TiffColor{TPixel}.cs

@ -16,11 +16,18 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
{ {
private readonly bool isBigEndian; private readonly bool isBigEndian;
private readonly Configuration configuration;
/// <summary> /// <summary>
/// Initializes a new instance of the <see cref="Rgb161616TiffColor{TPixel}" /> class. /// Initializes a new instance of the <see cref="Rgb161616TiffColor{TPixel}" /> class.
/// </summary> /// </summary>
/// <param name="configuration">The configuration.</param>
/// <param name="isBigEndian">if set to <c>true</c> decodes the pixel data as big endian, otherwise as little endian.</param> /// <param name="isBigEndian">if set to <c>true</c> decodes the pixel data as big endian, otherwise as little endian.</param>
public Rgb161616TiffColor(bool isBigEndian) => this.isBigEndian = isBigEndian; public Rgb161616TiffColor(Configuration configuration, bool isBigEndian)
{
this.configuration = configuration;
this.isBigEndian = isBigEndian;
}
/// <inheritdoc/> /// <inheritdoc/>
public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height) public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height)
@ -53,17 +60,14 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
} }
else else
{ {
for (int x = 0; x < pixelRow.Length; x++) int byteCount = pixelRow.Length * 6;
{ PixelOperations<TPixel>.Instance.FromRgb48Bytes(
ulong r = TiffUtils.ConvertToUShortLittleEndian(data.Slice(offset, 2)); this.configuration,
offset += 2; data.Slice(offset, byteCount),
ulong g = TiffUtils.ConvertToUShortLittleEndian(data.Slice(offset, 2)); pixelRow,
offset += 2; pixelRow.Length);
ulong b = TiffUtils.ConvertToUShortLittleEndian(data.Slice(offset, 2));
offset += 2;
pixelRow[x] = TiffUtils.ColorFromRgba64(rgba, r, g, b, color); offset += byteCount;
}
} }
} }
} }

28
src/ImageSharp/Formats/Tiff/PhotometricInterpretation/Rgb888TiffColor{TPixel}.cs

@ -2,7 +2,6 @@
// Licensed under the Apache License, Version 2.0. // Licensed under the Apache License, Version 2.0.
using System; using System;
using SixLabors.ImageSharp.Memory; using SixLabors.ImageSharp.Memory;
using SixLabors.ImageSharp.PixelFormats; using SixLabors.ImageSharp.PixelFormats;
@ -14,29 +13,26 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
internal class Rgb888TiffColor<TPixel> : TiffBaseColorDecoder<TPixel> internal class Rgb888TiffColor<TPixel> : TiffBaseColorDecoder<TPixel>
where TPixel : unmanaged, IPixel<TPixel> where TPixel : unmanaged, IPixel<TPixel>
{ {
private readonly Configuration configuration;
public Rgb888TiffColor(Configuration configuration) => this.configuration = configuration;
/// <inheritdoc/> /// <inheritdoc/>
public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height) public override void Decode(ReadOnlySpan<byte> data, Buffer2D<TPixel> pixels, int left, int top, int width, int height)
{ {
var color = default(TPixel);
int offset = 0; int offset = 0;
var rgba = default(Rgba32);
for (int y = top; y < top + height; y++) for (int y = top; y < top + height; y++)
{ {
Span<TPixel> pixelRow = pixels.GetRowSpan(y).Slice(left, width); Span<TPixel> pixelRow = pixels.GetRowSpan(y).Slice(left, width);
int byteCount = pixelRow.Length * 3;
for (int x = 0; x < pixelRow.Length; x++) PixelOperations<TPixel>.Instance.FromRgb24Bytes(
{ this.configuration,
byte r = data[offset++]; data.Slice(offset, byteCount),
byte g = data[offset++]; pixelRow,
byte b = data[offset++]; pixelRow.Length);
rgba.PackedValue = (uint)(r | (g << 8) | (b << 16) | (0xff << 24)); offset += byteCount;
color.FromRgba32(rgba);
pixelRow[x] = color;
}
} }
} }
} }

10
src/ImageSharp/Formats/Tiff/PhotometricInterpretation/TiffColorDecoderFactory{TPixel}.cs

@ -8,7 +8,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
internal static class TiffColorDecoderFactory<TPixel> internal static class TiffColorDecoderFactory<TPixel>
where TPixel : unmanaged, IPixel<TPixel> where TPixel : unmanaged, IPixel<TPixel>
{ {
public static TiffBaseColorDecoder<TPixel> Create(TiffColorType colorType, TiffBitsPerSample bitsPerSample, ushort[] colorMap, ByteOrder byteOrder) public static TiffBaseColorDecoder<TPixel> Create(Configuration configuration, TiffColorType colorType, TiffBitsPerSample bitsPerSample, ushort[] colorMap, ByteOrder byteOrder)
{ {
switch (colorType) switch (colorType)
{ {
@ -65,12 +65,12 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
case TiffColorType.BlackIsZero8: case TiffColorType.BlackIsZero8:
DebugGuard.IsTrue(bitsPerSample.Channels == 1 && bitsPerSample.Channel0 == 8, "bitsPerSample"); DebugGuard.IsTrue(bitsPerSample.Channels == 1 && bitsPerSample.Channel0 == 8, "bitsPerSample");
DebugGuard.IsTrue(colorMap == null, "colorMap"); DebugGuard.IsTrue(colorMap == null, "colorMap");
return new BlackIsZero8TiffColor<TPixel>(); return new BlackIsZero8TiffColor<TPixel>(configuration);
case TiffColorType.BlackIsZero16: case TiffColorType.BlackIsZero16:
DebugGuard.IsTrue(bitsPerSample.Channels == 1 && bitsPerSample.Channel0 == 16, "bitsPerSample"); DebugGuard.IsTrue(bitsPerSample.Channels == 1 && bitsPerSample.Channel0 == 16, "bitsPerSample");
DebugGuard.IsTrue(colorMap == null, "colorMap"); DebugGuard.IsTrue(colorMap == null, "colorMap");
return new BlackIsZero16TiffColor<TPixel>(byteOrder == ByteOrder.BigEndian); return new BlackIsZero16TiffColor<TPixel>(configuration, byteOrder == ByteOrder.BigEndian);
case TiffColorType.BlackIsZero24: case TiffColorType.BlackIsZero24:
DebugGuard.IsTrue(bitsPerSample.Channels == 1 && bitsPerSample.Channel0 == 24, "bitsPerSample"); DebugGuard.IsTrue(bitsPerSample.Channels == 1 && bitsPerSample.Channel0 == 24, "bitsPerSample");
@ -114,7 +114,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
&& bitsPerSample.Channel0 == 8, && bitsPerSample.Channel0 == 8,
"bitsPerSample"); "bitsPerSample");
DebugGuard.IsTrue(colorMap == null, "colorMap"); DebugGuard.IsTrue(colorMap == null, "colorMap");
return new Rgb888TiffColor<TPixel>(); return new Rgb888TiffColor<TPixel>(configuration);
case TiffColorType.Rgb101010: case TiffColorType.Rgb101010:
DebugGuard.IsTrue( DebugGuard.IsTrue(
@ -154,7 +154,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff.PhotometricInterpretation
&& bitsPerSample.Channel0 == 16, && bitsPerSample.Channel0 == 16,
"bitsPerSample"); "bitsPerSample");
DebugGuard.IsTrue(colorMap == null, "colorMap"); DebugGuard.IsTrue(colorMap == null, "colorMap");
return new Rgb161616TiffColor<TPixel>(isBigEndian: byteOrder == ByteOrder.BigEndian); return new Rgb161616TiffColor<TPixel>(configuration, isBigEndian: byteOrder == ByteOrder.BigEndian);
case TiffColorType.Rgb242424: case TiffColorType.Rgb242424:
DebugGuard.IsTrue( DebugGuard.IsTrue(

2
src/ImageSharp/Formats/Tiff/TiffDecoderCore.cs

@ -316,7 +316,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff
this.Predictor, this.Predictor,
this.FaxCompressionOptions); this.FaxCompressionOptions);
TiffBaseColorDecoder<TPixel> colorDecoder = TiffColorDecoderFactory<TPixel>.Create(this.ColorType, this.BitsPerSample, this.ColorMap, this.byteOrder); TiffBaseColorDecoder<TPixel> colorDecoder = TiffColorDecoderFactory<TPixel>.Create(this.Configuration, this.ColorType, this.BitsPerSample, this.ColorMap, this.byteOrder);
for (int stripIndex = 0; stripIndex < stripOffsets.Length; stripIndex++) for (int stripIndex = 0; stripIndex < stripOffsets.Length; stripIndex++)
{ {

2
tests/ImageSharp.Tests/Formats/Tiff/PhotometricInterpretation/BlackIsZeroTiffColorTests.cs

@ -188,7 +188,7 @@ namespace SixLabors.ImageSharp.Tests.Formats.Tiff.PhotometricInterpretation
{ {
AssertDecode(expectedResult, pixels => AssertDecode(expectedResult, pixels =>
{ {
new BlackIsZero8TiffColor<Rgba32>().Decode(inputData, pixels, left, top, width, height); new BlackIsZero8TiffColor<Rgba32>(Configuration.Default).Decode(inputData, pixels, left, top, width, height);
}); });
} }
} }

2
tests/ImageSharp.Tests/Formats/Tiff/PhotometricInterpretation/RgbTiffColorTests.cs

@ -179,7 +179,7 @@ namespace SixLabors.ImageSharp.Tests.Formats.Tiff.PhotometricInterpretation
{ {
AssertDecode(expectedResult, pixels => AssertDecode(expectedResult, pixels =>
{ {
new Rgb888TiffColor<Rgba32>().Decode(inputData, pixels, left, top, width, height); new Rgb888TiffColor<Rgba32>(Configuration.Default).Decode(inputData, pixels, left, top, width, height);
}); });
} }
} }

Loading…
Cancel
Save