Browse Source

fixing corner tiles

pull/673/head
popow 8 years ago
parent
commit
80660c935b
  1. 51
      src/ImageSharp/Processing/Processors/Normalization/AdaptiveHistEqualizationProcessor.cs

51
src/ImageSharp/Processing/Processors/Normalization/AdaptiveHistEqualizationProcessor.cs

@ -104,6 +104,41 @@ namespace SixLabors.ImageSharp.Processing.Processors.Normalization
// fix bottom row
this.ProcessBorderRow(source, pixels, cdfData, this.Tiles - 1, tileWidth, tileHeight, yStart: source.Height - halfTileHeight, yEnd: source.Height);
// left top corner
this.ProcessCornerTile(source, pixels, cdfData[0, 0], xStart: 0, xEnd: halfTileWidth, yStart: 0, yEnd: halfTileHeight, pixelsInTile: pixelsInTile);
// left bottom corner
this.ProcessCornerTile(source, pixels, cdfData[0, this.Tiles - 1], xStart: 0, xEnd: halfTileWidth, yStart: source.Height - halfTileHeight, yEnd: source.Height, pixelsInTile: pixelsInTile);
// right top corner
this.ProcessCornerTile(source, pixels, cdfData[this.Tiles - 1, 0], xStart: source.Width - halfTileWidth, xEnd: source.Width, yStart: 0, yEnd: halfTileHeight, pixelsInTile: pixelsInTile);
// right bottom corner
this.ProcessCornerTile(source, pixels, cdfData[this.Tiles - 1, this.Tiles - 1], xStart: source.Width - halfTileWidth, xEnd: source.Width, yStart: source.Height - halfTileHeight, yEnd: source.Height, pixelsInTile: pixelsInTile);
}
}
/// <summary>
/// Processes the part of a corner tile which was previously left out. It consists of 1 / 4 of a tile and does not need interpolation.
/// </summary>
/// <param name="source">The source image.</param>
/// <param name="pixels">The output pixels.</param>
/// <param name="cdfData">The lookup table to remap the grey values.</param>
/// <param name="xStart">X start position.</param>
/// <param name="xEnd">X end position.</param>
/// <param name="yStart">Y start position.</param>
/// <param name="yEnd">Y end position.</param>
/// <param name="pixelsInTile">Pixels in a tile.</param>
private void ProcessCornerTile(ImageFrame<TPixel> source, Span<TPixel> pixels, CdfData cdfData, int xStart, int xEnd, int yStart, int yEnd, int pixelsInTile)
{
for (int dy = yStart; dy < yEnd; dy++)
{
for (int dx = xStart; dx < xEnd; dx++)
{
float luminanceEqualized = cdfData.RemapGreyValue(this.GetLuminance(source[dx, dy], this.LuminanceLevels), pixelsInTile);
pixels[(dy * source.Width) + dx].PackFromVector4(new Vector4(luminanceEqualized));
}
}
}
@ -200,7 +235,7 @@ namespace SixLabors.ImageSharp.Processing.Processors.Normalization
/// <returns>A re-mapped grey value.</returns>
private float InterpolateBetweenFourTiles(TPixel sourcePixel, CdfData[,] cdfData, int tileX, int tileY, int cdfX, int cdfY, int tileWidth, int tileHeight, int pixelsInTile)
{
int luminace = this.GetLuminance(sourcePixel, this.LuminanceLevels);
int luminance = this.GetLuminance(sourcePixel, this.LuminanceLevels);
float tx = tileX / (float)(tileWidth - 1);
float ty = tileY / (float)(tileHeight - 1);
@ -209,10 +244,10 @@ namespace SixLabors.ImageSharp.Processing.Processors.Normalization
int xLeft = cdfX;
int xRight = Math.Min(this.Tiles - 1, xLeft + 1);
float cdfLeftTopLuminance = cdfData[xLeft, yTop].RemapGreyValue(luminace, pixelsInTile);
float cdfRightTopLuminance = cdfData[xRight, yTop].RemapGreyValue(luminace, pixelsInTile);
float cdfLeftBottomLuminance = cdfData[xLeft, yBottom].RemapGreyValue(luminace, pixelsInTile);
float cdfRightBottomLuminance = cdfData[xRight, yBottom].RemapGreyValue(luminace, pixelsInTile);
float cdfLeftTopLuminance = cdfData[xLeft, yTop].RemapGreyValue(luminance, pixelsInTile);
float cdfRightTopLuminance = cdfData[xRight, yTop].RemapGreyValue(luminance, pixelsInTile);
float cdfLeftBottomLuminance = cdfData[xLeft, yBottom].RemapGreyValue(luminance, pixelsInTile);
float cdfRightBottomLuminance = cdfData[xRight, yBottom].RemapGreyValue(luminance, pixelsInTile);
float luminanceEqualized = this.BilinearInterpolation(tx, ty, cdfLeftTopLuminance, cdfRightTopLuminance, cdfLeftBottomLuminance, cdfRightBottomLuminance);
return luminanceEqualized;
@ -230,11 +265,11 @@ namespace SixLabors.ImageSharp.Processing.Processors.Normalization
/// <returns>A re-mapped grey value.</returns>
private float InterpolateBetweenTwoTiles(TPixel sourcePixel, CdfData cdfData1, CdfData cdfData2, int tilePos, int tileWidth, int pixelsInTile)
{
int luminace = this.GetLuminance(sourcePixel, this.LuminanceLevels);
int luminance = this.GetLuminance(sourcePixel, this.LuminanceLevels);
float tx = tilePos / (float)(tileWidth - 1);
float cdfLuminance1 = cdfData1.RemapGreyValue(luminace, pixelsInTile);
float cdfLuminance2 = cdfData2.RemapGreyValue(luminace, pixelsInTile);
float cdfLuminance1 = cdfData1.RemapGreyValue(luminance, pixelsInTile);
float cdfLuminance2 = cdfData2.RemapGreyValue(luminance, pixelsInTile);
float luminanceEqualized = this.LinearInterpolation(cdfLuminance1, cdfLuminance2, tx);
return luminanceEqualized;

Loading…
Cancel
Save