7

MSDN reference: [1] http://msdn.microsoft.com/en-us/library/5ey6h79d.aspx#Y1178

From the link it says that the first argument will "specifies the portion of the Bitmap to lock" which I set to be a smaller part of the Bitmap (Bitmap is 500x500, my rectangle is (0,0,50,50)) however the returned BitmapData has stride of 1500 (=500*3) so basically every scan will still scan through the whole picture horizontally. However, what I want is only the top left 50x50 part of the bitmap.

How does this work out?

4

1 に答える 1

10

ストライドは常に完全なビットマップになりますが、Scan0 プロパティは、ロック四角形の開始点、および BitmapData の高さと幅によって異なります。

その理由は、行を反復処理する (アドレスにストライドを追加する) ために、ビットマップの実際のビット幅を知る必要があるためです。

それを行う簡単な方法は次のとおりです。

var bitmap = new Bitmap(100, 100);

var data = bitmap.LockBits(new Rectangle(0, 0, 10, 10),
                           ImageLockMode.ReadWrite,
                           bitmap.PixelFormat);

var pt = (byte*)data.Scan0;
var bpp = data.Stride / bitmap.Width;

for (var y = 0; y < data.Height; y++)
{
    // This is why real scan-width is important to have!
    var row = pt + (y * data.Stride);

    for (var x = 0; x < data.Width; x++)
    {
        var pixel = row + x * bpp;

        for (var bit = 0; bit < bpp; bit++)
        {
            var pixelComponent = pixel[bit];
        }
    }
}

bitmap.UnlockBits(data);

したがって、基本的にはビットマップ全体をロックするだけですが、ビットマップ内の四角形の左上のピクセルへのポインターを提供し、スキャンの幅と高さを適切に設定します。

于 2012-05-27T03:02:13.053 に答える