Reputation: 16282
Suppose i had two nearly identical images and i wanted to locate and highlight the differences between them and produce the diff image. the routine works but this routine ask to supply color which i do not want. here is my code.
public class ImageTool
{
public static unsafe Bitmap GetDifferenceImage(Bitmap image1, Bitmap image2, Color matchColor)
{
if (image1 == null | image2 == null)
return null;
if (image1.Height != image2.Height || image1.Width != image2.Width)
return null;
Bitmap diffImage = image2.Clone() as Bitmap;
int height = image1.Height;
int width = image1.Width;
BitmapData data1 = image1.LockBits(new Rectangle(0, 0, width, height),
ImageLockMode.ReadOnly, PixelFormat.Format24bppRgb);
BitmapData data2 = image2.LockBits(new Rectangle(0, 0, width, height),
ImageLockMode.ReadOnly, PixelFormat.Format24bppRgb);
BitmapData diffData = diffImage.LockBits(new Rectangle(0, 0, width, height),
ImageLockMode.WriteOnly, PixelFormat.Format24bppRgb);
byte* data1Ptr = (byte*)data1.Scan0;
byte* data2Ptr = (byte*)data2.Scan0;
byte* diffPtr = (byte*)diffData.Scan0;
byte[] swapColor = new byte[3];
swapColor[0] = matchColor.B;
swapColor[1] = matchColor.G;
swapColor[2] = matchColor.R;
int rowPadding = data1.Stride - (image1.Width * 3);
// iterate over height (rows)
for (int i = 0; i < height; i++)
{
// iterate over width (columns)
for (int j = 0; j < width; j++)
{
int same = 0;
byte[] tmp = new byte[3];
// compare pixels and copy new values into temporary array
for (int x = 0; x < 3; x++)
{
tmp[x] = data2Ptr[0];
if (data1Ptr[0] == data2Ptr[0])
{
same++;
}
data1Ptr++; // advance image1 ptr
data2Ptr++; // advance image2 ptr
}
// swap color or add new values
for (int x = 0; x < 3; x++)
{
diffPtr[0] = (same == 3) ? swapColor[x] : tmp[x];
diffPtr++; // advance diff image ptr
}
}
// at the end of each column, skip extra padding
if (rowPadding > 0)
{
data1Ptr += rowPadding;
data2Ptr += rowPadding;
diffPtr += rowPadding;
}
}
image1.UnlockBits(data1);
image2.UnlockBits(data2);
diffImage.UnlockBits(diffData);
return diffImage;
}
}
calling like this way:
Bitmap diff = ImageTool.GetDifferenceImage(image1, image2, Color.Pink);
diff.MakeTransparent(Color.Pink);
diff.Save("C:\\test-diff.png",ImageFormat.Png);
some one just guide me how to change this routine as a result we do not have to pass color when i will call GetDifferenceImage()
method.
this way image comparison is best technique if not then guide me how to develop a routine which can be more faster to get the diff image.
after getting the diff image how can i merge the diff image with image1
. help me to develop a faster merge routine.
Upvotes: 2
Views: 3454
Reputation: 3135
The diff image is black if two images are identical and has an increasing brightness for pixels with larger differences. You can just change the algorithm so that instead of assigning the pixel the swapcolor it assigns it the difference between the two colors.
// iterate over height (rows)
for (int i = 0; i < height; i++)
{
// iterate over width (columns)
for (int j = 0; j < width; j++)
{
// for each channel
for (int x=0; x<3; x++)
{
diffPtr[0] = Abs(data1Ptr[0]-data2Ptr[0]);
data1Ptr++; // advance image1 ptr
data2Ptr++; // advance image2 ptr
diffPtr++; // advance diff image ptr
}
}
// at the end of each column, skip extra padding
if (rowPadding > 0)
{
data1Ptr += rowPadding;
data2Ptr += rowPadding;
diffPtr += rowPadding;
}
}
How you show/merge the diff will depend on what you are going to do with it.
Upvotes: 5