私が書いている VNC タイプのアプリのパフォーマンスを最適化しようとしていますが、本当に最適化するのに少し苦労しています。
2 つのビットマップが与えられた場合、ビットマップ間の違いを完全に含む、可能な限り小さいサイズの 3 番目のビットマップを返したいと思います。
ビットマップ A / ビットマップ B と同じサイズのビットマップを返すことができます。違いには色があり、残りは透明ですが、実際のデータ スペースは節約されず、実際には何も最適化されません。 (ビットマップが完全に透明なピクセルで何か特別なことをしない限り、そうではないように感じます。)
とにかく、ここに私が今持っているものがあります。最初の変更が見つかったポインターを追跡し、最後の変更が見つかったポインターを追跡する可能性がありますが、これらのポインターを四角形に変換するにはどうすればよいですか? フルサイズの差分ビットマップをその四角形に切り抜くにはどうすればよいでしょうか?
これまでに使用したコードは次のとおりです。
var a = previous.Screen;
var b = next.Screen;
Bitmap output = new Bitmap(
Math.Max(a.Width, b.Width),
Math.Max(a.Height, b.Height),
PixelFormat.Format32bppArgb);
Rectangle recta = new Rectangle(Point.Empty, a.Size);
Rectangle rectb = new Rectangle(Point.Empty, b.Size);
Rectangle rectOutput = new Rectangle(Point.Empty, output.Size);
BitmapData aData = a.LockBits(recta, ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb);
BitmapData bData = b.LockBits(rectb, ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb);
BitmapData outputData = output.LockBits(rectOutput, ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);
try
{
unsafe
{
byte* aPtr = (byte*) aData.Scan0;
byte* bPtr = (byte*) bData.Scan0;
byte* outputPtr = (byte*) outputData.Scan0;
int h = Math.Min(a.Height, b.Height);
int w = Math.Min(a.Width, b.Width);
for (int y = 0; y < h; y++)
{
aPtr = (byte*) aData.Scan0;
bPtr = (byte*) bData.Scan0;
outputPtr = (byte*) outputData.Scan0;
aPtr += y*aData.Stride;
bPtr += y*bData.Stride;
outputPtr += y*outputData.Stride;
for (int x = 0; x < w; x++)
{
bool bl = false;
//the three color channels
for (int j = 0; j < 3; j++)
{
if (*aPtr != *bPtr)
{
bl = true;
}
*outputPtr = (byte) *bPtr;
outputPtr++;
aPtr++;
bPtr++;
}
//alpha, when one or mre color channels are different
if (bl)
*outputPtr = (byte) ((*aPtr + *bPtr)/2);
outputPtr++;
aPtr++;
bPtr++;
}
}
}
}
catch
{
if (output != null)
{
output.UnlockBits(outputData);
output.Dispose();
output = null;
}
}
finally
{
a.UnlockBits(aData);
b.UnlockBits(bData);
if (output != null)
output.UnlockBits(outputData);
}