
Introduction
This is my next article on image processing. Here one of the most important filtering methods called Homomorphic Filtering is discussed.
Homomorphic filtering is a generalized technique for signal and image processing, involving a nonlinear mapping to a different domain in which linear
filter techniques are applied, followed by mapping back to the original domain.
A homomorphic filter is sometimes used for image enhancement. It simultaneously normalizes the brightness across an image and increases contrast.
Here homomorphic filtering is used to remove multiplicative noise. Illumination and reflectance are not separable, but their approximate locations
in the frequency domain may be located. Since illumination and reflectance combine multiplicatively, the components are made additive by taking the logarithm
of the image intensity, so that these multiplicative components of the image can be separated linearly in the frequency domain. Illumination variations
can be thought of as a multiplicative noise, and can be reduced by filtering in the log domain.
To make the illumination of an image more even, the high-frequency components are increased and low-frequency components are decreased, because the high-frequency components
are assumed to represent mostly the reflectance in the scene (the amount of light reflected off the object in the scene), whereas the low-frequency components are assumed
to represent mostly the illumination in the scene. That is, high-pass filtering is used to suppress low frequencies and amplify high frequencies, in the log-intensity domain (from Wikipedia).
Using the code
The image is selected first. Then We use 2D FFT of the image, actually the LOG of image is taken to separate the intensity and reflection part of the image.
The High pass Gaussian filter is applied on the Reflection plane and then Inverse FFT is done.
The important code is given below.
public static COMPLEX[,] ApplyFilterHMMFreqDomain(COMPLEX[,] FFTData,
float rH, float rL, float Sigma, float Slope)
{
COMPLEX[,] Output = new COMPLEX[FFTData.GetLength(0), FFTData.GetLength(1)];
int i, j, W, H;
W = FFTData.GetLength(0);
H = FFTData.GetLength(1);
double Weight;
double[,] GaussianHPF =
GenerateGaussianKernelHPF(FFTData.GetLength(0), Sigma, Slope, out Weight);
COMPLEX[,] GaussianHPFFFT;
for (i = 0; i <= GaussianHPF.GetLength(0) - 1; i++)
for (j = 0; j <= GaussianHPF.GetLength(1) - 1; j++)
{
GaussianHPF[i, j] = GaussianHPF[i, j]; }
FFT GaussianFFTObject = new FFT(GaussianHPF);
GaussianFFTObject.ForwardFFT(GaussianHPF);
GaussianFFTObject.FFTShift();
GaussianHPFFFT = GaussianFFTObject.FFTShifted;
for (i = 0; i <= GaussianHPF.GetLength(0) - 1; i++)
for (j = 0; j <= GaussianHPF.GetLength(1) - 1; j++)
{
GaussianHPFFFT[i, j].real = (rH - rL) * GaussianHPFFFT[i, j].real + rL;
GaussianHPFFFT[i, j].imag = (rH - rL) * GaussianHPFFFT[i, j].imag + rL;
}
Output = MultiplyFFTMatrices(GaussianHPFFFT, FFTData);
return Output;
}
Points of Interest
This article is based on an important image processing technique. The code takes an image of any size but processes an image block of 256*256 pixels.
You can modify the code for higher sizes of images, by changing the concerned values.
History
You need to have an understanding of 2D FFT, so please read the article
http://www.codeproject.com/Articles/44166/2D-FFT-of-an-Image-in-C.