Browse Source

Quant table adjustment method

pull/1761/head
Dmitry Pentin 4 years ago
parent
commit
aae451c844
  1. 38
      src/ImageSharp/Formats/Jpeg/Components/Encoder/HuffmanScanEncoder.cs
  2. 19
      src/ImageSharp/Formats/Jpeg/Components/FastFloatingPointDCT.cs

38
src/ImageSharp/Formats/Jpeg/Components/Encoder/HuffmanScanEncoder.cs

@ -139,12 +139,8 @@ namespace SixLabors.ImageSharp.Formats.Jpeg.Components.Encoder
public void Encode444<TPixel>(Image<TPixel> pixels, ref Block8x8F luminanceQuantTable, ref Block8x8F chrominanceQuantTable, CancellationToken cancellationToken)
where TPixel : unmanaged, IPixel<TPixel>
{
// Calculate reciprocal quantization tables for FDCT method
for (int i = 0; i < Block8x8F.Size; i++)
{
luminanceQuantTable[i] = FastFloatingPointDCT.DctReciprocalAdjustmentCoefficients[i] / luminanceQuantTable[i];
chrominanceQuantTable[i] = FastFloatingPointDCT.DctReciprocalAdjustmentCoefficients[i] / chrominanceQuantTable[i];
}
FastFloatingPointDCT.AdjustToFDCT(ref luminanceQuantTable);
FastFloatingPointDCT.AdjustToFDCT(ref chrominanceQuantTable);
this.huffmanTables = HuffmanLut.TheHuffmanLut;
@ -206,12 +202,8 @@ namespace SixLabors.ImageSharp.Formats.Jpeg.Components.Encoder
public void Encode420<TPixel>(Image<TPixel> pixels, ref Block8x8F luminanceQuantTable, ref Block8x8F chrominanceQuantTable, CancellationToken cancellationToken)
where TPixel : unmanaged, IPixel<TPixel>
{
// Calculate reciprocal quantization tables for FDCT method
for (int i = 0; i < Block8x8F.Size; i++)
{
luminanceQuantTable[i] = FastFloatingPointDCT.DctReciprocalAdjustmentCoefficients[i] / luminanceQuantTable[i];
chrominanceQuantTable[i] = FastFloatingPointDCT.DctReciprocalAdjustmentCoefficients[i] / chrominanceQuantTable[i];
}
FastFloatingPointDCT.AdjustToFDCT(ref luminanceQuantTable);
FastFloatingPointDCT.AdjustToFDCT(ref chrominanceQuantTable);
this.huffmanTables = HuffmanLut.TheHuffmanLut;
@ -279,11 +271,7 @@ namespace SixLabors.ImageSharp.Formats.Jpeg.Components.Encoder
public void EncodeGrayscale<TPixel>(Image<TPixel> pixels, ref Block8x8F luminanceQuantTable, CancellationToken cancellationToken)
where TPixel : unmanaged, IPixel<TPixel>
{
// Calculate reciprocal quantization tables for FDCT method
for (int i = 0; i < Block8x8F.Size; i++)
{
luminanceQuantTable[i] = FastFloatingPointDCT.DctReciprocalAdjustmentCoefficients[i] / luminanceQuantTable[i];
}
FastFloatingPointDCT.AdjustToFDCT(ref luminanceQuantTable);
this.huffmanTables = HuffmanLut.TheHuffmanLut;
@ -325,16 +313,12 @@ namespace SixLabors.ImageSharp.Formats.Jpeg.Components.Encoder
/// </summary>
/// <typeparam name="TPixel">The pixel format.</typeparam>
/// <param name="pixels">The pixel accessor providing access to the image pixels.</param>
/// <param name="luminanceQuantTable">Luminance quantization table provided by the callee.</param>
/// <param name="quantTable">Quantization table provided by the callee.</param>
/// <param name="cancellationToken">The token to monitor for cancellation.</param>
public void EncodeRgb<TPixel>(Image<TPixel> pixels, ref Block8x8F luminanceQuantTable, CancellationToken cancellationToken)
public void EncodeRgb<TPixel>(Image<TPixel> pixels, ref Block8x8F quantTable, CancellationToken cancellationToken)
where TPixel : unmanaged, IPixel<TPixel>
{
// Calculate reciprocal quantization tables for FDCT method
for (int i = 0; i < Block8x8F.Size; i++)
{
luminanceQuantTable[i] = FastFloatingPointDCT.DctReciprocalAdjustmentCoefficients[i] / luminanceQuantTable[i];
}
FastFloatingPointDCT.AdjustToFDCT(ref quantTable);
this.huffmanTables = HuffmanLut.TheHuffmanLut;
@ -360,19 +344,19 @@ namespace SixLabors.ImageSharp.Formats.Jpeg.Components.Encoder
QuantIndex.Luminance,
prevDCR,
ref pixelConverter.R,
ref luminanceQuantTable);
ref quantTable);
prevDCG = this.WriteBlock(
QuantIndex.Luminance,
prevDCG,
ref pixelConverter.G,
ref luminanceQuantTable);
ref quantTable);
prevDCB = this.WriteBlock(
QuantIndex.Luminance,
prevDCB,
ref pixelConverter.B,
ref luminanceQuantTable);
ref quantTable);
if (this.IsStreamFlushNeeded)
{

19
src/ImageSharp/Formats/Jpeg/Components/FastFloatingPointDCT.cs

@ -62,10 +62,10 @@ namespace SixLabors.ImageSharp.Formats.Jpeg.Components
/// <code>
/// scalefactor[k] = cos(k*PI/16) * sqrt(2) for k=1..7
/// </code>
/// Values are also scaled by 8 so DCT code won't do unnecessary division.
/// Values are also scaled by 8 so DCT code won't do extra division/multiplication.
/// </para>
/// </remarks>
public static readonly float[] DctReciprocalAdjustmentCoefficients = new float[]
private static readonly float[] DctReciprocalAdjustmentCoefficients = new float[]
{
0.125f, 0.09011998f, 0.09567086f, 0.10630376f, 0.125f, 0.15909483f, 0.23096988f, 0.45306373f,
0.09011998f, 0.064972885f, 0.068974845f, 0.07664074f, 0.09011998f, 0.11470097f, 0.16652f, 0.32664075f,
@ -77,6 +77,21 @@ namespace SixLabors.ImageSharp.Formats.Jpeg.Components
0.45306373f, 0.32664075f, 0.34675997f, 0.38529903f, 0.45306373f, 0.5766407f, 0.8371526f, 1.642134f,
};
/// <summary>
/// Adjusts given quantization table to be complient with FDCT implementation.
/// </summary>
/// <remarks>
/// See <see cref="DctReciprocalAdjustmentCoefficients"/> docs for explanation.
/// </remarks>
/// <param name="quantizationtable">Quantization table to adjust.</param>
public static void AdjustToFDCT(ref Block8x8F quantizationtable)
{
for (int i = 0; i < Block8x8F.Size; i++)
{
quantizationtable[i] = DctReciprocalAdjustmentCoefficients[i] / quantizationtable[i];
}
}
/// <summary>
/// Apply 2D floating point FDCT inplace.
/// </summary>

Loading…
Cancel
Save