I'm trying to create some basic image process program, and if I go throw the image with two for
loops, then that's very slow, so, I tried with Parallel. For
but, with that, I have to lock
the image or copy to the temporary image in each loop, which is also not so fast, or even worst than a single for. So I thinking about, how can I copy just a row of an image, process it, and copy it back into the image, or, what is the best/better, and not so complicated method for this?
Easiest example: creating an inverse/negate image:
for (int i = 0; i < image.Height; i++)
for (int j = 0; j < image.Width; j++)
{
System.Drawing.Color c = image.GetPixel(j, i);
c = Color.FromArgb(255 - c.R, 255 - c.G, 255 - c.B);
image.SetPixel(j, i, c);
}
Thanks, for it!
UPDATE:
Here is a basic example of how to do it:
Bitmap image = new Bitmap(pictureBox.Image);
BitmapData bitmapData = image.LockBits(new Rectangle(0, 0, image.Width, image.Height), ImageLockMode.ReadWrite, image.PixelFormat); //reserve an area in memory which is equal to the image
int height = bitmapData.Height;
int bPP = System.Drawing.Bitmap.GetPixelFormatSize(image.PixelFormat) / 8; //pixels/byte
int width = bitmapData.Width*bPP;
unsafe //because of c# doesn't support well pointers
{
byte* firstPixel = (byte*)bitmapData.Scan0; //the fst pixel of the reserved area
Parallel.For(0, height, j =>
{
byte* line = firstPixel + (j * bitmapData.Stride); //iterate row by row from the fst pixel
for (int i = 0; i < width; i= i + bPP)//one pixel is 3 element in a row, in BGR order
{
int oldB = line[i];
int oldG = line[i+1];
int oldR = line[i+2];
line[i] = (byte) oldB;
line[i + 1] = (byte) oldG;
line[i + 2] = (byte) oldR;
}
});
image.UnlockBits(bitmapData);
}
pictureBox.Image = image;