3

我使用下面的代码克隆位图图像而不锁定原始文件。但我面临克隆图像(.Gif)与原始图像不同的问题。特别是克隆图像的颜色不合适。

我做错什么了吗?有没有更好的方法让内存中的图像和从硬盘中删除的原始文件?

代码:

private Bitmap CloneImage(Bitmap src)
    {
        if (src == null)
            return src;
        Bitmap bitmap = new Bitmap(src.Size.Width, src.Size.Height, src.PixelFormat);
        System.Drawing.Rectangle bounds = new System.Drawing.Rectangle(0, 0, src.Width, src.Height);
        System.Drawing.Imaging.BitmapData bmpData = src.LockBits(bounds, System.Drawing.Imaging.ImageLockMode.ReadWrite, src.PixelFormat);
        System.Drawing.Imaging.BitmapData newBmpData = bitmap.LockBits(bounds, System.Drawing.Imaging.ImageLockMode.ReadWrite, src.PixelFormat);
        IntPtr bPtr = bmpData.Scan0;
        IntPtr nbPtr = newBmpData.Scan0;
        int bytes = Math.Abs(bmpData.Stride) * src.Height;
        byte[] rgbValues = new byte[bytes];

        System.Runtime.InteropServices.Marshal.Copy(bPtr, rgbValues, 0, bytes);
        System.Runtime.InteropServices.Marshal.Copy(rgbValues, 0, nbPtr, bytes);
        bitmap.UnlockBits(newBmpData);
        src.UnlockBits(bmpData);
        return bitmap;
    }

原图:

原始图像

克隆图像:

克隆图像

4

3 回答 3

3

这看起来像调色板问题。各个像素位于正确的位置,因此 memcpy 代码可能是正确的。

也可以复制调色板,或者使用 24 位或 32 位像素格式并用于Graphics.FromImage将源图像blit 到目标位图上。然后你可以保存为 PNG,无论如何这可能会是一个较小的文件。

于 2013-10-07T11:54:36.507 回答
1

通过将图像保存到 MemoryStream 来克隆图像更容易(更少的代码)。然后您可以从 MemoryStream 加载它,您将拥有克隆的位图,并且您不必弄乱像素格式。

于 2013-10-07T11:54:59.720 回答
0

根据这个 SO answer,你在这里做的事情应该和,

private Bitmap CloneImage(Bitmap src)
{
  return new Bitmap(src);
}
于 2017-03-13T04:47:16.997 回答