/// <summary> /// Clears an image. /// </summary> /// <param name="image">Image to clear</param> /// <param name="clr">Color to clear to</param> public static void Clear(this Image image, Color clr) { unsafe { int srcBytesPerPixel = PixelFormatHelper.GetBytesPerPixel(image.PixelFormat); byte *srcRow = (byte *)image.ImageData.ToPointer(); for (int i = 0; i < image.Height; i++) { byte *srcCol = srcRow; for (int j = 0; j < image.Width; j++) { switch (image.PixelFormat) { case PixelFormat.Gray_8bpp: srcCol[0] = Image.Rgb2Gray(clr.R, clr.G, clr.B); break; case PixelFormat.Gray_16bpp: ((ushort *)srcCol)[0] = Image.Rgb2Gray((ushort)clr.R, (ushort)clr.G, (ushort)clr.B); break; case PixelFormat.BGR_24bpp: srcCol[2] = clr.R; srcCol[1] = clr.G; srcCol[0] = clr.B; break; case PixelFormat.BGRX_32bpp: srcCol[2] = clr.R; srcCol[1] = clr.G; srcCol[0] = clr.B; break; case PixelFormat.BGRA_32bpp: srcCol[3] = clr.R; srcCol[2] = clr.G; srcCol[1] = clr.B; srcCol[0] = clr.A; break; } srcCol += srcBytesPerPixel; } srcRow += image.Stride; } } }
/// <summary> /// Copies a source image into a destination image using the specified masking image. /// Only pixels in the source image whose corresponding mask image pixels are > 0 /// are copied to the destination image. Only pixels from the srcRect are copied /// to the destination rect. /// </summary> /// <param name="srcImage">Source image</param> /// <param name="srcRect">Source rectangle to copy from</param> /// <param name="dstImage">Destination image</param> /// <param name="dstRect">Destination rectangle to copy to</param> /// <param name="maskImage">Masking image</param> public static void CopyTo(this Image srcImage, Rectangle srcRect, Image dstImage, Rectangle dstRect, Image maskImage) { if (srcRect.Width != dstRect.Width || srcRect.Height != dstRect.Height) { throw new System.Exception("Source and destination rectangles sizes must match"); } if (maskImage != null) { if (srcImage.Width != maskImage.Width || srcImage.Height != maskImage.Height) { throw new System.Exception("Mask image size must match source image size"); } if (maskImage.PixelFormat != PixelFormat.Gray_8bpp) { throw new System.Exception("Mask image must be of type PixelFormat.Gray_8bpp"); } } PixelFormat srcFormat = srcImage.PixelFormat; PixelFormat dstFormat = dstImage.PixelFormat; System.IntPtr srcBuffer = srcImage.ImageData; System.IntPtr dstBuffer = dstImage.ImageData; System.IntPtr maskBuffer = (maskImage != null) ? maskImage.ImageData : System.IntPtr.Zero; unsafe { int srcBytesPerPixel = PixelFormatHelper.GetBytesPerPixel(srcFormat); int dstBytesPerPixel = PixelFormatHelper.GetBytesPerPixel(dstFormat); int maskBytesPerPixel = PixelFormatHelper.GetBytesPerPixel(PixelFormat.Gray_8bpp); byte *srcRow = (byte *)srcBuffer.ToPointer() + (srcRect.Y * srcImage.Stride) + (srcRect.X * srcBytesPerPixel); byte *dstRow = (byte *)dstBuffer.ToPointer() + (dstRect.Y * dstImage.Stride) + (dstRect.X * dstBytesPerPixel); byte *maskRow = null; if (maskImage != null) { maskRow = (byte *)maskBuffer.ToPointer() + (srcRect.Y * maskImage.Stride) + (srcRect.X * maskBytesPerPixel); } for (int i = 0; i < srcRect.Height; i++) { byte *srcCol = srcRow; byte *dstCol = dstRow; byte *maskCol = maskRow; for (int j = 0; j < srcRect.Width; j++) { bool copyPixel = true; if (maskImage != null) { if (*maskCol == 0) { copyPixel = false; } } if (copyPixel) { int red = 0; int green = 0; int blue = 0; int alpha = 255; switch (srcFormat) { case PixelFormat.Gray_8bpp: red = green = blue = srcCol[0]; break; case PixelFormat.Gray_16bpp: red = green = blue = ((ushort *)srcCol)[0]; break; case PixelFormat.BGR_24bpp: blue = srcCol[0]; green = srcCol[1]; red = srcCol[2]; break; case PixelFormat.BGRX_32bpp: blue = srcCol[0]; green = srcCol[1]; red = srcCol[2]; break; case PixelFormat.BGRA_32bpp: blue = srcCol[0]; green = srcCol[1]; red = srcCol[2]; alpha = srcCol[3]; break; case PixelFormat.RGBA_64bpp: red = ((ushort *)srcCol)[0]; green = ((ushort *)srcCol)[1]; blue = ((ushort *)srcCol)[2]; alpha = ((ushort *)srcCol)[3]; break; } switch (dstFormat) { case PixelFormat.Gray_8bpp: dstCol[0] = Image.Rgb2Gray((byte)red, (byte)green, (byte)blue); break; case PixelFormat.Gray_16bpp: ((ushort *)dstCol)[0] = Image.Rgb2Gray((ushort)red, (ushort)green, (ushort)blue); break; case PixelFormat.BGR_24bpp: case PixelFormat.BGRX_32bpp: dstCol[0] = (byte)blue; dstCol[1] = (byte)green; dstCol[2] = (byte)red; break; case PixelFormat.BGRA_32bpp: dstCol[0] = (byte)blue; dstCol[1] = (byte)green; dstCol[2] = (byte)red; dstCol[3] = (byte)alpha; break; case PixelFormat.RGBA_64bpp: ((ushort *)dstCol)[0] = (ushort)red; ((ushort *)dstCol)[1] = (ushort)green; ((ushort *)dstCol)[2] = (ushort)blue; ((ushort *)dstCol)[3] = (ushort)alpha; break; } } srcCol += srcBytesPerPixel; dstCol += dstBytesPerPixel; maskCol += maskBytesPerPixel; } srcRow += srcImage.Stride; dstRow += dstImage.Stride; if (maskImage != null) { maskRow += maskImage.Stride; } } } }