Skip to content

Commit 44b4651

Browse files
Merge pull request #1165 from SixLabors/bp/moreTgaTests
Additional tga tests for paletted RLE images
2 parents 557b1c5 + 6d115fe commit 44b4651

File tree

11 files changed

+124
-26
lines changed

11 files changed

+124
-26
lines changed

src/ImageSharp/Formats/Tga/TgaDecoderCore.cs

Lines changed: 17 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -252,14 +252,14 @@ private void ReadPaletted<TPixel>(int width, int height, Buffer2D<TPixel> pixels
252252
{
253253
for (int x = width - 1; x >= 0; x--)
254254
{
255-
this.ReadPalettedBgr16Pixel(palette, colorMapPixelSizeInBytes, x, color, pixelRow);
255+
this.ReadPalettedBgra16Pixel(palette, colorMapPixelSizeInBytes, x, color, pixelRow);
256256
}
257257
}
258258
else
259259
{
260260
for (int x = 0; x < width; x++)
261261
{
262-
this.ReadPalettedBgr16Pixel(palette, colorMapPixelSizeInBytes, x, color, pixelRow);
262+
this.ReadPalettedBgra16Pixel(palette, colorMapPixelSizeInBytes, x, color, pixelRow);
263263
}
264264
}
265265

@@ -321,7 +321,6 @@ private void ReadPalettedRle<TPixel>(int width, int height, Buffer2D<TPixel> pix
321321
using (IMemoryOwner<byte> buffer = this.memoryAllocator.Allocate<byte>(width * height * bytesPerPixel, AllocationOptions.Clean))
322322
{
323323
TPixel color = default;
324-
var alphaBits = this.tgaMetadata.AlphaChannelBits;
325324
Span<byte> bufferSpan = buffer.GetSpan();
326325
this.UncompressRle(width, height, bufferSpan, bytesPerPixel: 1);
327326

@@ -339,30 +338,13 @@ private void ReadPalettedRle<TPixel>(int width, int height, Buffer2D<TPixel> pix
339338
color.FromL8(Unsafe.As<byte, L8>(ref palette[bufferSpan[idx] * colorMapPixelSizeInBytes]));
340339
break;
341340
case 2:
342-
343-
Bgra5551 bgra = Unsafe.As<byte, Bgra5551>(ref palette[bufferSpan[idx] * colorMapPixelSizeInBytes]);
344-
if (!this.hasAlpha)
345-
{
346-
// Set alpha value to 1, to treat it as opaque for Bgra5551.
347-
bgra.PackedValue = (ushort)(bgra.PackedValue | 0x8000);
348-
}
349-
350-
color.FromBgra5551(bgra);
341+
this.ReadPalettedBgra16Pixel(palette, bufferSpan[idx], colorMapPixelSizeInBytes, ref color);
351342
break;
352343
case 3:
353344
color.FromBgr24(Unsafe.As<byte, Bgr24>(ref palette[bufferSpan[idx] * colorMapPixelSizeInBytes]));
354345
break;
355346
case 4:
356-
if (this.hasAlpha)
357-
{
358-
color.FromBgra32(Unsafe.As<byte, Bgra32>(ref palette[bufferSpan[idx] * colorMapPixelSizeInBytes]));
359-
}
360-
else
361-
{
362-
var alpha = alphaBits == 0 ? byte.MaxValue : bufferSpan[idx + 3];
363-
color.FromBgra32(new Bgra32(bufferSpan[idx + 2], bufferSpan[idx + 1], bufferSpan[idx], (byte)alpha));
364-
}
365-
347+
color.FromBgra32(Unsafe.As<byte, Bgra32>(ref palette[bufferSpan[idx] * colorMapPixelSizeInBytes]));
366348
break;
367349
}
368350

@@ -737,20 +719,29 @@ private void ReadBgra32Row<TPixel>(int width, Buffer2D<TPixel> pixels, IManagedB
737719
PixelOperations<TPixel>.Instance.FromBgra32Bytes(this.configuration, row.GetSpan(), pixelSpan, width);
738720
}
739721

740-
private void ReadPalettedBgr16Pixel<TPixel>(byte[] palette, int colorMapPixelSizeInBytes, int x, TPixel color, Span<TPixel> pixelRow)
722+
[MethodImpl(MethodImplOptions.AggressiveInlining)]
723+
private void ReadPalettedBgra16Pixel<TPixel>(byte[] palette, int colorMapPixelSizeInBytes, int x, TPixel color, Span<TPixel> pixelRow)
741724
where TPixel : unmanaged, IPixel<TPixel>
742725
{
743726
int colorIndex = this.currentStream.ReadByte();
727+
this.ReadPalettedBgra16Pixel(palette, colorIndex, colorMapPixelSizeInBytes, ref color);
728+
pixelRow[x] = color;
729+
}
730+
731+
[MethodImpl(MethodImplOptions.AggressiveInlining)]
732+
private void ReadPalettedBgra16Pixel<TPixel>(byte[] palette, int index, int colorMapPixelSizeInBytes, ref TPixel color)
733+
where TPixel : unmanaged, IPixel<TPixel>
734+
{
744735
Bgra5551 bgra = default;
745-
bgra.FromBgra5551(Unsafe.As<byte, Bgra5551>(ref palette[colorIndex * colorMapPixelSizeInBytes]));
736+
bgra.FromBgra5551(Unsafe.As<byte, Bgra5551>(ref palette[index * colorMapPixelSizeInBytes]));
737+
746738
if (!this.hasAlpha)
747739
{
748-
// Set alpha value to 1, to treat it as opaque for Bgra5551.
740+
// Set alpha value to 1, to treat it as opaque.
749741
bgra.PackedValue = (ushort)(bgra.PackedValue | 0x8000);
750742
}
751743

752744
color.FromBgra5551(bgra);
753-
pixelRow[x] = color;
754745
}
755746

756747
[MethodImpl(MethodImplOptions.AggressiveInlining)]

tests/ImageSharp.Tests/Formats/Tga/TgaDecoderTests.cs

Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
using SixLabors.ImageSharp.Formats.Tga;
77
using SixLabors.ImageSharp.Memory;
88
using SixLabors.ImageSharp.PixelFormats;
9+
using SixLabors.ImageSharp.Processing;
910
using SixLabors.ImageSharp.Tests.TestUtilities;
1011
using SixLabors.ImageSharp.Tests.TestUtilities.ImageComparison;
1112
using Xunit;
@@ -499,6 +500,54 @@ public void TgaDecoder_CanDecode_RunLengthEncoded_WithBottomRightOrigin_32Bit<TP
499500
}
500501
}
501502

503+
[Theory]
504+
[WithFile(Bit32PalRleTopLeft, PixelTypes.Rgba32)]
505+
public void TgaDecoder_CanDecode_RLE_Paletted_WithTopLeftOrigin_32Bit<TPixel>(TestImageProvider<TPixel> provider)
506+
where TPixel : unmanaged, IPixel<TPixel>
507+
{
508+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
509+
{
510+
image.DebugSave(provider);
511+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
512+
}
513+
}
514+
515+
[Theory]
516+
[WithFile(Bit32PalRleBottomLeft, PixelTypes.Rgba32)]
517+
public void TgaDecoder_CanDecode_RLE_Paletted_WithBottomLeftOrigin_32Bit<TPixel>(TestImageProvider<TPixel> provider)
518+
where TPixel : unmanaged, IPixel<TPixel>
519+
{
520+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
521+
{
522+
image.DebugSave(provider);
523+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
524+
}
525+
}
526+
527+
[Theory]
528+
[WithFile(Bit32PalRleTopRight, PixelTypes.Rgba32)]
529+
public void TgaDecoder_CanDecode_RLE_WithTopRightOrigin_32Bit<TPixel>(TestImageProvider<TPixel> provider)
530+
where TPixel : unmanaged, IPixel<TPixel>
531+
{
532+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
533+
{
534+
image.DebugSave(provider);
535+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
536+
}
537+
}
538+
539+
[Theory]
540+
[WithFile(Bit32PalRleBottomRight, PixelTypes.Rgba32)]
541+
public void TgaDecoder_CanDecode_RLE_Paletted_WithBottomRightOrigin_32Bit<TPixel>(TestImageProvider<TPixel> provider)
542+
where TPixel : unmanaged, IPixel<TPixel>
543+
{
544+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
545+
{
546+
image.DebugSave(provider);
547+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
548+
}
549+
}
550+
502551
[Theory]
503552
[WithFile(Bit16PalBottomLeft, PixelTypes.Rgba32)]
504553
public void TgaDecoder_CanDecode_WithPaletteBottomLeftOrigin_16Bit<TPixel>(TestImageProvider<TPixel> provider)
@@ -559,6 +608,54 @@ public void TgaDecoder_CanDecode_WithPaletteBottomRightOrigin_24Bit<TPixel>(Test
559608
}
560609
}
561610

611+
[Theory]
612+
[WithFile(Bit24PalRleTopLeft, PixelTypes.Rgba32)]
613+
public void TgaDecoder_CanDecode_RLE_WithPaletteTopLeftOrigin_24Bit<TPixel>(TestImageProvider<TPixel> provider)
614+
where TPixel : unmanaged, IPixel<TPixel>
615+
{
616+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
617+
{
618+
image.DebugSave(provider);
619+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
620+
}
621+
}
622+
623+
[Theory]
624+
[WithFile(Bit24PalRleTopRight, PixelTypes.Rgba32)]
625+
public void TgaDecoder_CanDecode_RLE_WithPaletteTopRightOrigin_24Bit<TPixel>(TestImageProvider<TPixel> provider)
626+
where TPixel : unmanaged, IPixel<TPixel>
627+
{
628+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
629+
{
630+
image.DebugSave(provider);
631+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
632+
}
633+
}
634+
635+
[Theory]
636+
[WithFile(Bit24PalRleBottomLeft, PixelTypes.Rgba32)]
637+
public void TgaDecoder_CanDecode_RLE_WithPaletteBottomLeftOrigin_24Bit<TPixel>(TestImageProvider<TPixel> provider)
638+
where TPixel : unmanaged, IPixel<TPixel>
639+
{
640+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
641+
{
642+
image.DebugSave(provider);
643+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
644+
}
645+
}
646+
647+
[Theory]
648+
[WithFile(Bit24PalRleBottomRight, PixelTypes.Rgba32)]
649+
public void TgaDecoder_CanDecode_RLE_WithPaletteBottomRightOrigin_24Bit<TPixel>(TestImageProvider<TPixel> provider)
650+
where TPixel : unmanaged, IPixel<TPixel>
651+
{
652+
using (Image<TPixel> image = provider.GetImage(TgaDecoder))
653+
{
654+
image.DebugSave(provider);
655+
TgaTestUtils.CompareWithReferenceDecoder(provider, image);
656+
}
657+
}
658+
562659
[Theory]
563660
[WithFile(Bit32PalTopLeft, PixelTypes.Rgba32)]
564661
public void TgaDecoder_CanDecode_WithPalette_32Bit<TPixel>(TestImageProvider<TPixel> provider)

tests/ImageSharp.Tests/TestImages.cs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -420,6 +420,11 @@ public static class Tga
420420
public const string Bit24PalBottomLeft = "Tga/targa_24bit_pal.tga";
421421
public const string Bit24PalBottomRight = "Tga/indexed_LR.tga";
422422

423+
public const string Bit24PalRleTopLeft = "Tga/indexed_rle_UL.tga";
424+
public const string Bit24PalRleBottomLeft = "Tga/indexed_rle_LL.tga";
425+
public const string Bit24PalRleTopRight = "Tga/indexed_rle_UR.tga";
426+
public const string Bit24PalRleBottomRight = "Tga/indexed_rle_LR.tga";
427+
423428
public const string Bit32TopLeft = "Tga/rgb_a_UL.tga";
424429
public const string Bit32BottomLeft = "Tga/targa_32bit.tga";
425430
public const string Bit32TopRight = "Tga/rgb_a_UR.tga";
@@ -435,6 +440,11 @@ public static class Tga
435440
public const string Bit32RleBottomRight = "Tga/rgb_a_rle_LR.tga";
436441
public const string Bit32RleBottomLeft = "Tga/targa_32bit_rle.tga";
437442

443+
public const string Bit32PalRleTopLeft = "Tga/indexed_a_rle_UL.tga";
444+
public const string Bit32PalRleBottomLeft = "Tga/indexed_a_rle_LL.tga";
445+
public const string Bit32PalRleTopRight = "Tga/indexed_a_rle_UR.tga";
446+
public const string Bit32PalRleBottomRight = "Tga/indexed_a_rle_LR.tga";
447+
438448
public const string NoAlphaBits16Bit = "Tga/16bit_noalphabits.tga";
439449
public const string NoAlphaBits16BitRle = "Tga/16bit_rle_noalphabits.tga";
440450
public const string NoAlphaBits32Bit = "Tga/32bit_no_alphabits.tga";
30.9 KB
Binary file not shown.
31 KB
Binary file not shown.
31 KB
Binary file not shown.
30.9 KB
Binary file not shown.
29.8 KB
Binary file not shown.
29.9 KB
Binary file not shown.
29.9 KB
Binary file not shown.

0 commit comments

Comments
 (0)