diff --git a/src/ImageSharp/Processing/Normalization/HistogramEqualizationProcessor.cs b/src/ImageSharp/Processing/Normalization/HistogramEqualizationProcessor.cs
index 6558f4889..ac6d23725 100644
--- a/src/ImageSharp/Processing/Normalization/HistogramEqualizationProcessor.cs
+++ b/src/ImageSharp/Processing/Normalization/HistogramEqualizationProcessor.cs
@@ -2,6 +2,7 @@
// Licensed under the Apache License, Version 2.0.
using System;
+using System.Numerics;
using SixLabors.ImageSharp.Advanced;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.ImageSharp.Processing.Processors;
@@ -20,8 +21,6 @@ namespace SixLabors.ImageSharp.Processing.Normalization
///
protected override void OnFrameApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration)
{
- var rgb48 = default(Rgb48);
- var rgb24 = default(Rgb24);
MemoryAllocator memoryAllocator = configuration.MemoryAllocator;
int numberOfPixels = source.Width * source.Height;
bool is16bitPerChannel = typeof(TPixel) == typeof(Rgb48) || typeof(TPixel) == typeof(Rgba64);
@@ -37,7 +36,7 @@ namespace SixLabors.ImageSharp.Processing.Normalization
for (int i = 0; i < pixels.Length; i++)
{
TPixel sourcePixel = pixels[i];
- int luminance = this.GetLuminance(sourcePixel, is16bitPerChannel, ref rgb24, ref rgb48);
+ int luminance = this.GetLuminance(sourcePixel, luminanceLevels);
histogram[luminance]++;
}
@@ -47,23 +46,14 @@ namespace SixLabors.ImageSharp.Processing.Normalization
// apply the cdf to each pixel of the image
double numberOfPixelsMinusCdfMin = (double)(numberOfPixels - cdfMin);
- int luminanceLevelsMinusOne = luminanceLevels - 1;
for (int i = 0; i < pixels.Length; i++)
{
TPixel sourcePixel = pixels[i];
- int luminance = this.GetLuminance(sourcePixel, is16bitPerChannel, ref rgb24, ref rgb48);
- double luminanceEqualized = (cdf[luminance] / numberOfPixelsMinusCdfMin) * luminanceLevelsMinusOne;
- luminanceEqualized = Math.Round(luminanceEqualized);
+ int luminance = this.GetLuminance(sourcePixel, luminanceLevels);
+ double luminanceEqualized = cdf[luminance] / numberOfPixelsMinusCdfMin;
- if (is16bitPerChannel)
- {
- pixels[i].PackFromRgb48(new Rgb48((ushort)luminanceEqualized, (ushort)luminanceEqualized, (ushort)luminanceEqualized));
- }
- else
- {
- pixels[i].PackFromRgba32(new Rgba32((byte)luminanceEqualized, (byte)luminanceEqualized, (byte)luminanceEqualized));
- }
+ pixels[i].PackFromVector4(new Vector4((float)luminanceEqualized));
}
}
}
@@ -108,23 +98,12 @@ namespace SixLabors.ImageSharp.Processing.Normalization
/// Convert the pixel values to grayscale using ITU-R Recommendation BT.709.
///
/// The pixel to get the luminance from
- /// Flag indicates, if its 16 bits per channel, otherwise its 8
- /// Will store the pixel values in case of 8 bit per channel
- /// Will store the pixel values in case of 16 bit per channel
- private int GetLuminance(TPixel sourcePixel, bool is16bitPerChannel, ref Rgb24 rgb24, ref Rgb48 rgb48)
+ /// The number of luminance levels (256 for 8 bit, 65536 for 16 bit grayscale images)
+ private int GetLuminance(TPixel sourcePixel, int luminanceLevels)
{
// Convert to grayscale using ITU-R Recommendation BT.709
- int luminance;
- if (is16bitPerChannel)
- {
- sourcePixel.ToRgb48(ref rgb48);
- luminance = Convert.ToInt32((.2126F * rgb48.R) + (.7152F * rgb48.G) + (.0722F * rgb48.B));
- }
- else
- {
- sourcePixel.ToRgb24(ref rgb24);
- luminance = Convert.ToInt32((.2126F * rgb24.R) + (.7152F * rgb24.G) + (.0722F * rgb24.B));
- }
+ var vector = sourcePixel.ToVector4();
+ int luminance = Convert.ToInt32(((.2126F * vector.X) + (.7152F * vector.Y) + (.0722F * vector.Y)) * luminanceLevels);
return luminance;
}