Home > programming > C#でBitmapの比較

C#でBitmapの比較

一定時間毎にWebブラウザのウィンドウをキャプチャして,変更の有無を検出するコードを書いていたんだけど,ちょっと引っかかってしまったのでメモ.

最初,BitmapクラスにはGetHashCodeというメンバ関数があるから,ハッシュを取得してそれを比較すれば良いだろう,と簡単に考えていた.ところが,GetHashCodeというのはオブジェクトのハッシュを返す関数であり,画像データのハッシュを返すわけではない.つまり,この関数の返り値を比較しても,画像の内容が等しいか否かを判断することが出来ない.

じゃぁ,1pixelごと比較すれば良いのかと考えたのだけれども,BitmapクラスのGetPixelメソッドって,メチャクチャ遅い.そこで,Bitmapの中身をbyte配列に代入して,そのMD5をとることでハッシュ値を取得し,それを比較することで画像の変更の有無を検出することにした.

以下,具体的なコード.これだけの事なんだけど,思ったよりも時間を取ってしまった・・・.

Bitmap CurrentImg = GetScreenCaputureOf(Firefox);
BitmapData bmpdata = CurrentImg.LockBits(new Rectangle(0, 0, CurrentImg.Width, CurrentImg.Height), ImageLockMode.ReadWrite, CurrentImg.PixelFormat);
IntPtr ptr = bmpdata.Scan0;
int bytes = bmpdata.Stride * CurrentImg.Height;
byte[] rgbValues = new byte[bytes];
Marshal.Copy(ptr, rgbValues, 0, bytes);
byte[] CurrentHash = new MD5CryptoServiceProvider().ComputeHash(rgbValues);

bool bEqual = false;
if (PrevHash!=null && PrevHash.Length == CurrentHash.Length)
{
    int i = 0;
    while ((i < PrevHash.Length) && (PrevHash[i] == CurrentHash[i]))
    {
        i += 1;
    }
    if (i == PrevHash.Length)
    {
        bEqual = true;
    }
}

PrevHash = (byte[])CurrentHash.Clone();
if (!bEqual)
{
    Console.WriteLine("Image Changed!");
}

参考にしたページ

Comments:0

Comment Form
Remember personal info

Trackbacks:0

Trackback URL for this entry
http://kur.jp/2010/03/03/bitmap-compare/trackback/
Listed below are links to weblogs that reference
C#でBitmapの比較 from kur.jp

Home > programming > C#でBitmapの比較

はてなブックマーク
なかのひと


Return to page top