32bpp [P]ARGB ピクセル形式を使用している場合、これは LockBits/BitmapData を使用して問題なく動作するはずです。コツは、データを一度に 1 行ずつコピーして、正しい場所に配置する必要があることです。次のようなものを使用してこれを行うことができるはずです。
Rectangle srcArea = new Rectangle(0, 0, srcBitmap.Width, srcBitmap.Height);
BitmapData srcData = srcBitmap.LockBits(srcArea, ImageLockMode.ReadOnly, destBitmap.PixelFormat);
Rectangle destArea = new Rectangle(25, 25, srcBitmap.Width, srcBitmap.Height);
BitmapData destData = destBitmap.LockBits(destArea, ImageLockMode.WriteOnly, destBitmap.PixelFormat);
IntPtr srcPtr = srcData.Scan0;
IntPtr destPtr = destData.Scan0;
byte[] buffer = new byte[srcData.Stride];
for (int i = 0; i < srcData.Height; ++i)
{
Marshal.Copy(srcPtr, buffer, 0, buffer.Length);
Marshal.Copy(buffer, 0, destPtr, buffer.Length);
srcPtr += srcData.Stride;
destPtr += destData.Stride;
}
srcBitmap.UnlockBits(srcData);
destBitmap.UnlockBits(destData);
警告として、このコードはそのままでは機能しません。なぜなら、IntPtr をインクリメントするための正しい呪文がわからないからです。私は以前にこれと同じタイプのことをしましたが、C++ で行いました。また、中間バッファーを使用する代わりに、データを直接コピーする方法があるかどうかもわかりません。
追加の警告: LockBits 呼び出し srcBitmap とバッファーのサイズ設定では、srcBitmap が destBitmap に完全に囲まれることを前提としています。そうでない場合 (ビットマップの一部が切り取られる)、領域がロックされ、バッファのサイズを調整する必要があります。
32bpp ピクセル形式 (つまり 24bpp) を使用していない場合は、さらに難しくなります。ソース BitmapData のストライドには、コピーしてはならない量のパディングが含まれている場合があります。ソース行の実際のピクセル データの量を計算し、この量をコピーすることで、これを回避できます。インデックス付きのピクセル形式はさらに手間がかかります。