Browse Source

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

# Conflicts:
#	src/ImageSharp/Formats/Tiff/Compression/TiffDecompressorsFactory.cs
#	src/ImageSharp/Formats/Tiff/TiffDecoderCore.cs
pull/1729/head
Brian Popow 5 years ago
parent
commit
6182eea673
  1. 7
      src/ImageSharp/Formats/Tiff/Compression/Decompressors/ModifiedHuffmanTiffCompression.cs
  2. 29
      src/ImageSharp/Formats/Tiff/Compression/Decompressors/T4BitReader.cs
  3. 53
      src/ImageSharp/Formats/Tiff/Compression/Decompressors/T4TiffCompression.cs
  4. 5
      src/ImageSharp/Formats/Tiff/Compression/TiffDecompressorsFactory.cs
  5. 4
      src/ImageSharp/Formats/Tiff/README.md
  6. 7
      src/ImageSharp/Formats/Tiff/TiffDecoderCore.cs
  7. 5
      src/ImageSharp/Formats/Tiff/TiffDecoderOptionsParser.cs
  8. 5
      tests/ImageSharp.Tests/Formats/Tiff/TiffDecoderTests.cs
  9. 6
      tests/ImageSharp.Tests/Formats/Tiff/TiffEncoderTests.cs
  10. 10
      tests/ImageSharp.Tests/Memory/Allocators/ArrayPoolMemoryAllocatorTests.cs
  11. 5
      tests/ImageSharp.Tests/TestImages.cs
  12. 4
      tests/Images/Input/Tiff/7324fcaff3aad96f27899da51c1bb5d9.tiff
  13. 4
      tests/Images/Input/Tiff/Calliphora_ccitt_fax3.tiff
  14. 3
      tests/Images/Input/Tiff/b0350_fillorder2.tiff
  15. 3
      tests/Images/Input/Tiff/basi3p02_fax3_lowerOrderBitsFirst.tiff
  16. 3
      tests/Images/Input/Tiff/basi3p02_huffman_rle_lowerOrderBitsFirst.tiff
  17. 3
      tests/Images/Input/Tiff/f8179f8f5e566349cf3583a1ff3ea95c.tiff
  18. 3
      tests/Images/Input/Tiff/g3test.tiff

7
src/ImageSharp/Formats/Tiff/Compression/Decompressors/ModifiedHuffmanTiffCompression.cs

@ -22,11 +22,12 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
/// Initializes a new instance of the <see cref="ModifiedHuffmanTiffCompression" /> class. /// Initializes a new instance of the <see cref="ModifiedHuffmanTiffCompression" /> class.
/// </summary> /// </summary>
/// <param name="allocator">The memory allocator.</param> /// <param name="allocator">The memory allocator.</param>
/// <param name="fillOrder">The logical order of bits within a byte.</param>
/// <param name="width">The image width.</param> /// <param name="width">The image width.</param>
/// <param name="bitsPerPixel">The number of bits per pixel.</param> /// <param name="bitsPerPixel">The number of bits per pixel.</param>
/// <param name="photometricInterpretation">The photometric interpretation.</param> /// <param name="photometricInterpretation">The photometric interpretation.</param>
public ModifiedHuffmanTiffCompression(MemoryAllocator allocator, int width, int bitsPerPixel, TiffPhotometricInterpretation photometricInterpretation) public ModifiedHuffmanTiffCompression(MemoryAllocator allocator, TiffFillOrder fillOrder, int width, int bitsPerPixel, TiffPhotometricInterpretation photometricInterpretation)
: base(allocator, width, bitsPerPixel, FaxCompressionOptions.None, photometricInterpretation) : base(allocator, fillOrder, width, bitsPerPixel, FaxCompressionOptions.None, photometricInterpretation)
{ {
bool isWhiteZero = photometricInterpretation == TiffPhotometricInterpretation.WhiteIsZero; bool isWhiteZero = photometricInterpretation == TiffPhotometricInterpretation.WhiteIsZero;
this.whiteValue = (byte)(isWhiteZero ? 0 : 1); this.whiteValue = (byte)(isWhiteZero ? 0 : 1);
@ -36,7 +37,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
/// <inheritdoc/> /// <inheritdoc/>
protected override void Decompress(BufferedReadStream stream, int byteCount, Span<byte> buffer) protected override void Decompress(BufferedReadStream stream, int byteCount, Span<byte> buffer)
{ {
using var bitReader = new T4BitReader(stream, byteCount, this.Allocator, eolPadding: false, isModifiedHuffman: true); using var bitReader = new T4BitReader(stream, this.FillOrder, byteCount, this.Allocator, eolPadding: false, isModifiedHuffman: true);
buffer.Clear(); buffer.Clear();
uint bitsWritten = 0; uint bitsWritten = 0;

29
src/ImageSharp/Formats/Tiff/Compression/Decompressors/T4BitReader.cs

@ -5,7 +5,8 @@ using System;
using System.Buffers; using System.Buffers;
using System.Collections.Generic; using System.Collections.Generic;
using System.IO; using System.IO;
using System.Runtime.CompilerServices;
using SixLabors.ImageSharp.Formats.Tiff.Constants;
using SixLabors.ImageSharp.Memory; using SixLabors.ImageSharp.Memory;
namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
@ -20,6 +21,11 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
/// </summary> /// </summary>
private int bitsRead; private int bitsRead;
/// <summary>
/// The logical order of bits within a byte.
/// </summary>
private readonly TiffFillOrder fillOrder;
/// <summary> /// <summary>
/// Current value. /// Current value.
/// </summary> /// </summary>
@ -221,12 +227,14 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
/// Initializes a new instance of the <see cref="T4BitReader" /> class. /// Initializes a new instance of the <see cref="T4BitReader" /> class.
/// </summary> /// </summary>
/// <param name="input">The compressed input stream.</param> /// <param name="input">The compressed input stream.</param>
/// <param name="fillOrder">The logical order of bits within a byte.</param>
/// <param name="bytesToRead">The number of bytes to read from the stream.</param> /// <param name="bytesToRead">The number of bytes to read from the stream.</param>
/// <param name="allocator">The memory allocator.</param> /// <param name="allocator">The memory allocator.</param>
/// <param name="eolPadding">Indicates, if fill bits have been added as necessary before EOL codes such that EOL always ends on a byte boundary. Defaults to false.</param> /// <param name="eolPadding">Indicates, if fill bits have been added as necessary before EOL codes such that EOL always ends on a byte boundary. Defaults to false.</param>
/// <param name="isModifiedHuffman">Indicates, if its the modified huffman code variation. Defaults to false.</param> /// <param name="isModifiedHuffman">Indicates, if its the modified huffman code variation. Defaults to false.</param>
public T4BitReader(Stream input, int bytesToRead, MemoryAllocator allocator, bool eolPadding = false, bool isModifiedHuffman = false) public T4BitReader(Stream input, TiffFillOrder fillOrder, int bytesToRead, MemoryAllocator allocator, bool eolPadding = false, bool isModifiedHuffman = false)
{ {
this.fillOrder = fillOrder;
this.Data = allocator.Allocate<byte>(bytesToRead); this.Data = allocator.Allocate<byte>(bytesToRead);
this.ReadImageDataFromStream(input, bytesToRead); this.ReadImageDataFromStream(input, bytesToRead);
@ -375,7 +383,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
break; break;
} }
var currBit = this.ReadValue(1); uint currBit = this.ReadValue(1);
this.value = (this.value << 1) | currBit; this.value = (this.value << 1) | currBit;
if (this.IsEndOfScanLine) if (this.IsEndOfScanLine)
@ -816,7 +824,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
Span<byte> dataSpan = this.Data.GetSpan(); Span<byte> dataSpan = this.Data.GetSpan();
int shift = 8 - this.bitsRead - 1; int shift = 8 - this.bitsRead - 1;
var bit = (uint)((dataSpan[(int)this.position] & (1 << shift)) != 0 ? 1 : 0); uint bit = (uint)((dataSpan[(int)this.position] & (1 << shift)) != 0 ? 1 : 0);
this.bitsRead++; this.bitsRead++;
return bit; return bit;
@ -837,6 +845,19 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
{ {
Span<byte> dataSpan = this.Data.GetSpan(); Span<byte> dataSpan = this.Data.GetSpan();
input.Read(dataSpan, 0, bytesToRead); input.Read(dataSpan, 0, bytesToRead);
if (this.fillOrder == TiffFillOrder.LeastSignificantBitFirst)
{
for (int i = 0; i < dataSpan.Length; i++)
{
dataSpan[i] = ReverseBits(dataSpan[i]);
}
}
} }
// http://graphics.stanford.edu/~seander/bithacks.html#ReverseByteWith64Bits
[MethodImpl(MethodImplOptions.AggressiveInlining)]
private static byte ReverseBits(byte b) =>
(byte)((((b * 0x80200802UL) & 0x0884422110UL) * 0x0101010101UL) >> 32);
} }
} }

53
src/ImageSharp/Formats/Tiff/Compression/Decompressors/T4TiffCompression.cs

@ -20,24 +20,33 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
private readonly byte blackValue; private readonly byte blackValue;
private readonly int width;
/// <summary> /// <summary>
/// Initializes a new instance of the <see cref="T4TiffCompression" /> class. /// Initializes a new instance of the <see cref="T4TiffCompression" /> class.
/// </summary> /// </summary>
/// <param name="allocator">The memory allocator.</param> /// <param name="allocator">The memory allocator.</param>
/// <param name="fillOrder">The logical order of bits within a byte.</param>
/// <param name="width">The image width.</param> /// <param name="width">The image width.</param>
/// <param name="bitsPerPixel">The number of bits per pixel.</param> /// <param name="bitsPerPixel">The number of bits per pixel.</param>
/// <param name="faxOptions">Fax compression options.</param> /// <param name="faxOptions">Fax compression options.</param>
/// <param name="photometricInterpretation">The photometric interpretation.</param> /// <param name="photometricInterpretation">The photometric interpretation.</param>
public T4TiffCompression(MemoryAllocator allocator, int width, int bitsPerPixel, FaxCompressionOptions faxOptions, TiffPhotometricInterpretation photometricInterpretation) public T4TiffCompression(MemoryAllocator allocator, TiffFillOrder fillOrder, int width, int bitsPerPixel, FaxCompressionOptions faxOptions, TiffPhotometricInterpretation photometricInterpretation)
: base(allocator, width, bitsPerPixel) : base(allocator, width, bitsPerPixel)
{ {
this.faxCompressionOptions = faxOptions; this.faxCompressionOptions = faxOptions;
this.FillOrder = fillOrder;
this.width = width;
bool isWhiteZero = photometricInterpretation == TiffPhotometricInterpretation.WhiteIsZero; bool isWhiteZero = photometricInterpretation == TiffPhotometricInterpretation.WhiteIsZero;
this.whiteValue = (byte)(isWhiteZero ? 0 : 1); this.whiteValue = (byte)(isWhiteZero ? 0 : 1);
this.blackValue = (byte)(isWhiteZero ? 1 : 0); this.blackValue = (byte)(isWhiteZero ? 1 : 0);
} }
/// <summary>
/// Gets the logical order of bits within a byte.
/// </summary>
protected TiffFillOrder FillOrder { get; }
/// <inheritdoc/> /// <inheritdoc/>
protected override void Decompress(BufferedReadStream stream, int byteCount, Span<byte> buffer) protected override void Decompress(BufferedReadStream stream, int byteCount, Span<byte> buffer)
{ {
@ -46,27 +55,22 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
TiffThrowHelper.ThrowNotSupported("TIFF CCITT 2D compression is not yet supported"); TiffThrowHelper.ThrowNotSupported("TIFF CCITT 2D compression is not yet supported");
} }
var eolPadding = this.faxCompressionOptions.HasFlag(FaxCompressionOptions.EolPadding); bool eolPadding = this.faxCompressionOptions.HasFlag(FaxCompressionOptions.EolPadding);
using var bitReader = new T4BitReader(stream, byteCount, this.Allocator, eolPadding); using var bitReader = new T4BitReader(stream, this.FillOrder, byteCount, this.Allocator, eolPadding);
buffer.Clear(); buffer.Clear();
uint bitsWritten = 0; uint bitsWritten = 0;
uint pixelWritten = 0;
while (bitReader.HasMoreData) while (bitReader.HasMoreData)
{ {
bitReader.ReadNextRun(); bitReader.ReadNextRun();
if (bitReader.RunLength > 0) if (bitReader.RunLength > 0)
{ {
if (bitReader.IsWhiteRun) this.WritePixelRun(buffer, bitReader, bitsWritten);
{
BitWriterUtils.WriteBits(buffer, (int)bitsWritten, bitReader.RunLength, this.whiteValue); bitsWritten += bitReader.RunLength;
bitsWritten += bitReader.RunLength; pixelWritten += bitReader.RunLength;
}
else
{
BitWriterUtils.WriteBits(buffer, (int)bitsWritten, bitReader.RunLength, this.blackValue);
bitsWritten += bitReader.RunLength;
}
} }
if (bitReader.IsEndOfScanLine) if (bitReader.IsEndOfScanLine)
@ -78,8 +82,29 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression.Decompressors
BitWriterUtils.WriteBits(buffer, (int)bitsWritten, pad, 0); BitWriterUtils.WriteBits(buffer, (int)bitsWritten, pad, 0);
bitsWritten += pad; bitsWritten += pad;
} }
pixelWritten = 0;
} }
} }
// Edge case for when we are at the last byte, but there are still some unwritten pixels left.
if (pixelWritten > 0 && pixelWritten < this.width)
{
bitReader.ReadNextRun();
this.WritePixelRun(buffer, bitReader, bitsWritten);
}
}
private void WritePixelRun(Span<byte> buffer, T4BitReader bitReader, uint bitsWritten)
{
if (bitReader.IsWhiteRun)
{
BitWriterUtils.WriteBits(buffer, (int)bitsWritten, bitReader.RunLength, this.whiteValue);
}
else
{
BitWriterUtils.WriteBits(buffer, (int)bitsWritten, bitReader.RunLength, this.blackValue);
}
} }
/// <inheritdoc/> /// <inheritdoc/>

5
src/ImageSharp/Formats/Tiff/Compression/TiffDecompressorsFactory.cs

@ -19,6 +19,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression
TiffColorType colorType, TiffColorType colorType,
TiffPredictor predictor, TiffPredictor predictor,
FaxCompressionOptions faxOptions, FaxCompressionOptions faxOptions,
TiffFillOrder fillOrder,
ByteOrder byteOrder) ByteOrder byteOrder)
{ {
switch (method) switch (method)
@ -43,11 +44,11 @@ namespace SixLabors.ImageSharp.Formats.Tiff.Compression
case TiffDecoderCompressionType.T4: case TiffDecoderCompressionType.T4:
DebugGuard.IsTrue(predictor == TiffPredictor.None, "Predictor should only be used with lzw or deflate compression"); DebugGuard.IsTrue(predictor == TiffPredictor.None, "Predictor should only be used with lzw or deflate compression");
return new T4TiffCompression(allocator, width, bitsPerPixel, faxOptions, photometricInterpretation); return new T4TiffCompression(allocator, fillOrder, width, bitsPerPixel, faxOptions, photometricInterpretation);
case TiffDecoderCompressionType.HuffmanRle: case TiffDecoderCompressionType.HuffmanRle:
DebugGuard.IsTrue(predictor == TiffPredictor.None, "Predictor should only be used with lzw or deflate compression"); DebugGuard.IsTrue(predictor == TiffPredictor.None, "Predictor should only be used with lzw or deflate compression");
return new ModifiedHuffmanTiffCompression(allocator, width, bitsPerPixel, photometricInterpretation); return new ModifiedHuffmanTiffCompression(allocator, fillOrder, width, bitsPerPixel, photometricInterpretation);
default: default:
throw TiffThrowHelper.NotSupportedDecompressor(nameof(method)); throw TiffThrowHelper.NotSupportedDecompressor(nameof(method));

4
src/ImageSharp/Formats/Tiff/README.md

@ -25,7 +25,7 @@
## Implementation Status ## Implementation Status
- The Decoder and Encoder currently only supports a single frame per image. - The Decoder currently only supports a single frame per image.
- Some compression formats are not yet supported. See the list below. - Some compression formats are not yet supported. See the list below.
### Deviations from the TIFF spec (to be fixed) ### Deviations from the TIFF spec (to be fixed)
@ -81,7 +81,7 @@
|Thresholding | | | | |Thresholding | | | |
|CellWidth | | | | |CellWidth | | | |
|CellLength | | | | |CellLength | | | |
|FillOrder | | - | Ignore. In practice is very uncommon, and is not recommended. | |FillOrder | | Y | |
|ImageDescription | Y | Y | | |ImageDescription | Y | Y | |
|Make | Y | Y | | |Make | Y | Y | |
|Model | Y | Y | | |Model | Y | Y | |

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

@ -85,6 +85,11 @@ namespace SixLabors.ImageSharp.Formats.Tiff
/// </summary> /// </summary>
public FaxCompressionOptions FaxCompressionOptions { get; set; } public FaxCompressionOptions FaxCompressionOptions { get; set; }
/// <summary>
/// Gets or sets the the logical order of bits within a byte.
/// </summary>
public TiffFillOrder FillOrder { get; set; }
/// <summary> /// <summary>
/// Gets or sets the planar configuration type to use when decoding the image. /// Gets or sets the planar configuration type to use when decoding the image.
/// </summary> /// </summary>
@ -273,6 +278,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff
this.ColorType, this.ColorType,
this.Predictor, this.Predictor,
this.FaxCompressionOptions, this.FaxCompressionOptions,
this.FillOrder,
this.byteOrder); this.byteOrder);
TiffBasePlanarColorDecoder<TPixel> colorDecoder = TiffColorDecoderFactory<TPixel>.CreatePlanar(this.ColorType, this.BitsPerSample, this.ColorMap, this.byteOrder); TiffBasePlanarColorDecoder<TPixel> colorDecoder = TiffColorDecoderFactory<TPixel>.CreatePlanar(this.ColorType, this.BitsPerSample, this.ColorMap, this.byteOrder);
@ -325,6 +331,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff
this.ColorType, this.ColorType,
this.Predictor, this.Predictor,
this.FaxCompressionOptions, this.FaxCompressionOptions,
this.FillOrder,
this.byteOrder); this.byteOrder);
TiffBaseColorDecoder<TPixel> colorDecoder = TiffColorDecoderFactory<TPixel>.Create(this.Configuration, this.ColorType, this.BitsPerSample, this.ColorMap, this.byteOrder); TiffBaseColorDecoder<TPixel> colorDecoder = TiffColorDecoderFactory<TPixel>.Create(this.Configuration, this.ColorType, this.BitsPerSample, this.ColorMap, this.byteOrder);

5
src/ImageSharp/Formats/Tiff/TiffDecoderOptionsParser.cs

@ -35,9 +35,9 @@ namespace SixLabors.ImageSharp.Formats.Tiff
} }
TiffFillOrder fillOrder = (TiffFillOrder?)exifProfile.GetValue(ExifTag.FillOrder)?.Value ?? TiffFillOrder.MostSignificantBitFirst; TiffFillOrder fillOrder = (TiffFillOrder?)exifProfile.GetValue(ExifTag.FillOrder)?.Value ?? TiffFillOrder.MostSignificantBitFirst;
if (fillOrder != TiffFillOrder.MostSignificantBitFirst) if (fillOrder == TiffFillOrder.LeastSignificantBitFirst && frameMetadata.BitsPerPixel != TiffBitsPerPixel.Bit1)
{ {
TiffThrowHelper.ThrowNotSupported("The lower-order bits of the byte FillOrder is not supported."); TiffThrowHelper.ThrowNotSupported("The lower-order bits of the byte FillOrder is only supported in combination with 1bit per pixel bicolor tiff's.");
} }
if (frameMetadata.Predictor == TiffPredictor.FloatingPoint) if (frameMetadata.Predictor == TiffPredictor.FloatingPoint)
@ -69,6 +69,7 @@ namespace SixLabors.ImageSharp.Formats.Tiff
options.PhotometricInterpretation = frameMetadata.PhotometricInterpretation ?? TiffPhotometricInterpretation.Rgb; options.PhotometricInterpretation = frameMetadata.PhotometricInterpretation ?? TiffPhotometricInterpretation.Rgb;
options.BitsPerPixel = frameMetadata.BitsPerPixel != null ? (int)frameMetadata.BitsPerPixel.Value : (int)TiffBitsPerPixel.Bit24; options.BitsPerPixel = frameMetadata.BitsPerPixel != null ? (int)frameMetadata.BitsPerPixel.Value : (int)TiffBitsPerPixel.Bit24;
options.BitsPerSample = frameMetadata.BitsPerSample ?? new TiffBitsPerSample(0, 0, 0); options.BitsPerSample = frameMetadata.BitsPerSample ?? new TiffBitsPerSample(0, 0, 0);
options.FillOrder = fillOrder;
options.ParseColorType(exifProfile); options.ParseColorType(exifProfile);
options.ParseCompression(frameMetadata.Compression, exifProfile); options.ParseCompression(frameMetadata.Compression, exifProfile);

5
tests/ImageSharp.Tests/Formats/Tiff/TiffDecoderTests.cs

@ -313,6 +313,11 @@ namespace SixLabors.ImageSharp.Tests.Formats.Tiff
public void TiffDecoder_CanDecode_Fax3Compressed<TPixel>(TestImageProvider<TPixel> provider) public void TiffDecoder_CanDecode_Fax3Compressed<TPixel>(TestImageProvider<TPixel> provider)
where TPixel : unmanaged, IPixel<TPixel> => TestTiffDecoder(provider); where TPixel : unmanaged, IPixel<TPixel> => TestTiffDecoder(provider);
[Theory]
[WithFile(CcittFax3LowerOrderBitsFirst, PixelTypes.Rgba32)]
public void TiffDecoder_CanDecode_Compressed_LowerOrderBitsFirst<TPixel>(TestImageProvider<TPixel> provider)
where TPixel : unmanaged, IPixel<TPixel> => TestTiffDecoder(provider);
[Theory] [Theory]
[WithFile(Calliphora_RgbPackbits, PixelTypes.Rgba32)] [WithFile(Calliphora_RgbPackbits, PixelTypes.Rgba32)]
[WithFile(RgbPackbits, PixelTypes.Rgba32)] [WithFile(RgbPackbits, PixelTypes.Rgba32)]

6
tests/ImageSharp.Tests/Formats/Tiff/TiffEncoderTests.cs

@ -117,7 +117,11 @@ namespace SixLabors.ImageSharp.Tests.Formats.Tiff
[InlineData(TiffPhotometricInterpretation.Rgb, TiffCompression.Jpeg, TiffBitsPerPixel.Bit24, TiffCompression.None)] [InlineData(TiffPhotometricInterpretation.Rgb, TiffCompression.Jpeg, TiffBitsPerPixel.Bit24, TiffCompression.None)]
[InlineData(TiffPhotometricInterpretation.Rgb, TiffCompression.OldDeflate, TiffBitsPerPixel.Bit24, TiffCompression.None)] [InlineData(TiffPhotometricInterpretation.Rgb, TiffCompression.OldDeflate, TiffBitsPerPixel.Bit24, TiffCompression.None)]
[InlineData(TiffPhotometricInterpretation.Rgb, TiffCompression.OldJpeg, TiffBitsPerPixel.Bit24, TiffCompression.None)] [InlineData(TiffPhotometricInterpretation.Rgb, TiffCompression.OldJpeg, TiffBitsPerPixel.Bit24, TiffCompression.None)]
public void EncoderOptions_SetPhotometricInterpretationAndCompression_Works(TiffPhotometricInterpretation? photometricInterpretation, TiffCompression compression, TiffBitsPerPixel expectedBitsPerPixel, TiffCompression expectedCompression) public void EncoderOptions_SetPhotometricInterpretationAndCompression_Works(
TiffPhotometricInterpretation? photometricInterpretation,
TiffCompression compression,
TiffBitsPerPixel expectedBitsPerPixel,
TiffCompression expectedCompression)
{ {
// arrange // arrange
var tiffEncoder = new TiffEncoder { PhotometricInterpretation = photometricInterpretation, Compression = compression }; var tiffEncoder = new TiffEncoder { PhotometricInterpretation = photometricInterpretation, Compression = compression };

10
tests/ImageSharp.Tests/Memory/Allocators/ArrayPoolMemoryAllocatorTests.cs

@ -11,6 +11,7 @@ using Xunit;
namespace SixLabors.ImageSharp.Tests.Memory.Allocators namespace SixLabors.ImageSharp.Tests.Memory.Allocators
{ {
[Collection("RunSerial")]
public class ArrayPoolMemoryAllocatorTests public class ArrayPoolMemoryAllocatorTests
{ {
private const int MaxPooledBufferSizeInBytes = 2048; private const int MaxPooledBufferSizeInBytes = 2048;
@ -56,19 +57,14 @@ namespace SixLabors.ImageSharp.Tests.Memory.Allocators
[Fact] [Fact]
public void When_PoolSelectorThresholdInBytes_IsGreaterThan_MaxPooledBufferSizeInBytes_ExceptionIsThrown() public void When_PoolSelectorThresholdInBytes_IsGreaterThan_MaxPooledBufferSizeInBytes_ExceptionIsThrown()
{ => Assert.ThrowsAny<Exception>(() => new ArrayPoolMemoryAllocator(100, 200));
Assert.ThrowsAny<Exception>(() => new ArrayPoolMemoryAllocator(100, 200));
}
} }
[Theory] [Theory]
[InlineData(32)] [InlineData(32)]
[InlineData(512)] [InlineData(512)]
[InlineData(MaxPooledBufferSizeInBytes - 1)] [InlineData(MaxPooledBufferSizeInBytes - 1)]
public void SmallBuffersArePooled_OfByte(int size) public void SmallBuffersArePooled_OfByte(int size) => Assert.True(this.LocalFixture.CheckIsRentingPooledBuffer<byte>(size));
{
Assert.True(this.LocalFixture.CheckIsRentingPooledBuffer<byte>(size));
}
[Theory] [Theory]
[InlineData(128 * 1024 * 1024)] [InlineData(128 * 1024 * 1024)]

5
tests/ImageSharp.Tests/TestImages.cs

@ -539,6 +539,8 @@ namespace SixLabors.ImageSharp.Tests
public const string CcittFax3AllMakeupCodes = "Tiff/ccitt_fax3_all_makeup_codes.tiff"; public const string CcittFax3AllMakeupCodes = "Tiff/ccitt_fax3_all_makeup_codes.tiff";
public const string HuffmanRleAllTermCodes = "Tiff/huffman_rle_all_terminating_codes.tiff"; public const string HuffmanRleAllTermCodes = "Tiff/huffman_rle_all_terminating_codes.tiff";
public const string HuffmanRleAllMakeupCodes = "Tiff/huffman_rle_all_makeup_codes.tiff"; public const string HuffmanRleAllMakeupCodes = "Tiff/huffman_rle_all_makeup_codes.tiff";
public const string CcittFax3LowerOrderBitsFirst = "Tiff/basi3p02_fax3_lowerOrderBitsFirst.tiff";
public const string HuffmanRleLowerOrderBitsFirst = "Tiff/basi3p02_huffman_rle_lowerOrderBitsFirst.tiff";
// Test case for an issue, that the last bits in a row got ignored. // Test case for an issue, that the last bits in a row got ignored.
public const string HuffmanRle_basi3p02 = "Tiff/basi3p02_huffman_rle.tiff"; public const string HuffmanRle_basi3p02 = "Tiff/basi3p02_huffman_rle.tiff";
@ -627,7 +629,6 @@ namespace SixLabors.ImageSharp.Tests
public const string MultiframeDifferentSize = "Tiff/multipage_differentSize.tiff"; public const string MultiframeDifferentSize = "Tiff/multipage_differentSize.tiff";
public const string MultiframeDifferentVariants = "Tiff/multipage_differentVariants.tiff"; public const string MultiframeDifferentVariants = "Tiff/multipage_differentVariants.tiff";
public const string FillOrder2 = "Tiff/b0350_fillorder2.tiff";
public const string LittleEndianByteOrder = "Tiff/little_endian.tiff"; public const string LittleEndianByteOrder = "Tiff/little_endian.tiff";
public const string Fax4_Motorola = "Tiff/moy.tiff"; public const string Fax4_Motorola = "Tiff/moy.tiff";
@ -642,7 +643,7 @@ namespace SixLabors.ImageSharp.Tests
public static readonly string[] Metadata = { SampleMetadata }; public static readonly string[] Metadata = { SampleMetadata };
public static readonly string[] NotSupported = { Calliphora_RgbJpeg, RgbJpeg, RgbUncompressedTiled, MultiframeDifferentSize, MultiframeDifferentVariants, FillOrder2, Calliphora_Fax4Compressed, Fax4_Motorola }; public static readonly string[] NotSupported = { Calliphora_RgbJpeg, RgbJpeg, RgbUncompressedTiled, MultiframeDifferentSize, MultiframeDifferentVariants, Calliphora_Fax4Compressed, Fax4_Motorola };
} }
} }
} }

4
tests/Images/Input/Tiff/7324fcaff3aad96f27899da51c1bb5d9.tiff

@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:622d69dba0a8a67aa3b87e384a2b9ea8d29689eaa5cb5d0eee857f98ed660517 oid sha256:579db6b2bd34566846de992f255c6b341d0f88d957a0eb02b01caad3f20c5b44
size 15154924 size 78794

4
tests/Images/Input/Tiff/Calliphora_ccitt_fax3.tiff

@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:8b9b105857723bca5f478a9ab23c0aeca93abe863781019bbd2da47f18c46f24 oid sha256:bba35f1e43c8425f3bcfab682efae4d2c00c62f0d8a4b411e646d32047469526
size 125778 size 125802

3
tests/Images/Input/Tiff/b0350_fillorder2.tiff

@ -1,3 +0,0 @@
version https://git-lfs.github.com/spec/v1
oid sha256:37c6a28f460d8781fdc3bcf0cc9bd23f633b03899563546bfc6234a8478f67f0
size 68637

3
tests/Images/Input/Tiff/basi3p02_fax3_lowerOrderBitsFirst.tiff

@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:eb56b3582c5c7d91d712e68181110ab0bf74d21992030629f05803c420b7b483
size 388

3
tests/Images/Input/Tiff/basi3p02_huffman_rle_lowerOrderBitsFirst.tiff

@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:5ac3e56a93996464a579ae19cf5f8d9531e2f08db36879aaba176731c24951a5
size 352

3
tests/Images/Input/Tiff/f8179f8f5e566349cf3583a1ff3ea95c.tiff

@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:cf75c4b679d2449e239f228cdee6a25adc7d7b16dde3fb9061a07b2fb0699db1
size 735412

3
tests/Images/Input/Tiff/g3test.tiff

@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:d5b2e1a17338133aa95cb8a16d82a171f5b50f7b9ae1a51ab06227dc3daa81d5
size 50401
Loading…
Cancel
Save