Browse Source

Reading transformation data

pull/1147/head
Brian Popow 7 years ago
parent
commit
e3946d82b0
  1. 21
      src/ImageSharp/Formats/WebP/Vp8LTransform.cs
  2. 36
      src/ImageSharp/Formats/WebP/WebPLosslessDecoder.cs

21
src/ImageSharp/Formats/WebP/Vp8LTransform.cs

@ -8,12 +8,17 @@ namespace SixLabors.ImageSharp.Formats.WebP
/// </summary> /// </summary>
internal class Vp8LTransform internal class Vp8LTransform
{ {
public Vp8LTransform(Vp8LTransformType transformType) => this.TransformType = transformType; public Vp8LTransform(Vp8LTransformType transformType, int xSize, int ySize)
{
this.TransformType = transformType;
this.XSize = xSize;
this.YSize = ySize;
}
/// <summary> /// <summary>
/// Gets or sets the transform type. /// Gets the transform type.
/// </summary> /// </summary>
public Vp8LTransformType TransformType { get; private set; } public Vp8LTransformType TransformType { get; }
/// <summary> /// <summary>
/// Subsampling bits defining transform window. /// Subsampling bits defining transform window.
@ -21,18 +26,18 @@ namespace SixLabors.ImageSharp.Formats.WebP
public int Bits { get; set; } public int Bits { get; set; }
/// <summary> /// <summary>
/// Transform window X index. /// Gets or sets the transform window X index.
/// </summary> /// </summary>
public int XSize { get; set; } public int XSize { get; set; }
/// <summary> /// <summary>
/// Transform window Y index. /// Gets the transform window Y index.
/// </summary> /// </summary>
public int YSize { get; set; } public int YSize { get; }
/// <summary> /// <summary>
/// Transform data. /// Gets or sets the transform data.
/// </summary> /// </summary>
public int[] Data { get; set; } public uint[] Data { get; set; }
} }
} }

36
src/ImageSharp/Formats/WebP/WebPLosslessDecoder.cs

@ -90,7 +90,7 @@ namespace SixLabors.ImageSharp.Formats.WebP
{ {
if (isLevel0) if (isLevel0)
{ {
this.ReadTransformations(decoder); this.ReadTransformations(xSize, ySize, decoder);
} }
// Color cache. // Color cache.
@ -571,7 +571,7 @@ namespace SixLabors.ImageSharp.Formats.WebP
/// Reads the transformations, if any are present. /// Reads the transformations, if any are present.
/// </summary> /// </summary>
/// <param name="decoder">Vp8LDecoder where the transformations will be stored.</param> /// <param name="decoder">Vp8LDecoder where the transformations will be stored.</param>
private void ReadTransformations(Vp8LDecoder decoder) private void ReadTransformations(int xSize, int ySize, Vp8LDecoder decoder)
{ {
// Next bit indicates, if a transformation is present. // Next bit indicates, if a transformation is present.
bool transformPresent = this.bitReader.ReadBit(); bool transformPresent = this.bitReader.ReadBit();
@ -580,7 +580,7 @@ namespace SixLabors.ImageSharp.Formats.WebP
while (transformPresent) while (transformPresent)
{ {
var transformType = (Vp8LTransformType)this.bitReader.ReadBits(2); var transformType = (Vp8LTransformType)this.bitReader.ReadBits(2);
var transform = new Vp8LTransform(transformType); var transform = new Vp8LTransform(transformType, xSize, ySize);
switch (transformType) switch (transformType)
{ {
case Vp8LTransformType.SubtractGreen: case Vp8LTransformType.SubtractGreen:
@ -589,29 +589,23 @@ namespace SixLabors.ImageSharp.Formats.WebP
case Vp8LTransformType.ColorIndexingTransform: case Vp8LTransformType.ColorIndexingTransform:
// The transform data contains color table size and the entries in the color table. // The transform data contains color table size and the entries in the color table.
// 8 bit value for color table size. // 8 bit value for color table size.
uint colorTableSize = this.bitReader.ReadBits(8) + 1; uint numColors = this.bitReader.ReadBits(8) + 1;
int bits = (numColors > 16) ? 0
// TODO: color table should follow here? : (numColors > 4) ? 1
: (numColors > 2) ? 2
: 3;
transform.XSize = LosslessUtils.SubSampleSize(transform.XSize, bits);
break; break;
case Vp8LTransformType.PredictorTransform: case Vp8LTransformType.PredictorTransform:
{
// The first 3 bits of prediction data define the block width and height in number of bits.
// The number of block columns, block_xsize, is used in indexing two-dimensionally.
uint sizeBits = this.bitReader.ReadBits(3) + 2;
int blockWidth = 1 << (int)sizeBits;
int blockHeight = 1 << (int)sizeBits;
break;
}
case Vp8LTransformType.CrossColorTransform: case Vp8LTransformType.CrossColorTransform:
{ {
// The first 3 bits of the color transform data contain the width and height of the image block in number of bits, transform.Bits = (int)this.bitReader.ReadBits(3) + 2;
// just like the predictor transform: transform.Data = this.DecodeImageStream(
uint sizeBits = this.bitReader.ReadBits(3) + 2; decoder,
int blockWidth = 1 << (int)sizeBits; LosslessUtils.SubSampleSize(transform.XSize, transform.Bits),
int blockHeight = 1 << (int)sizeBits; LosslessUtils.SubSampleSize(transform.YSize, transform.Bits),
false);
break; break;
} }
} }

Loading…
Cancel
Save