I am developing a program which gets Image from a Camera device. Here is the event how I get the Image.
private void StreamGrabber_ImageGrabbed(object sender, ImageGrabbedEventArgs e)
{
IGrabResult res = e.GrabResult;
byte[] pixels = res.PixelData as byte[];
pictureBox1.Image = ByteArrayToBitmap(pixels,res.Width,res.Height, PixelFormat.Format8bppIndexed);
//ImagePersistence.Save(ImageFileFormat.Jpeg, "tmp/tmp" + i + ".jpg", img);
}
I can get the Pixel Data Array with the code above. And I can directly save the image with the single line of code.
ImagePersistence.Save(ImageFileFormat.Jpeg, "tmp/tmp" + i + ".jpg", img);
Now my problem starts here. I don't want to save it, I just want to create the Bitmap object from pixel data and simply show in my pictureBox1 object. I have pixel data of image but in any case I couldn't get the image correctly.
Here is ByteArrayToBitmap function;
public Bitmap ByteArrayToBitmap(byte[] byteIn, int imwidth, int imheight, PixelFormat pixelformat)
{
Bitmap picOut = new Bitmap(imwidth, imheight, pixelformat);
BitmapData bmpData = picOut.LockBits(new Rectangle(0, 0, imwidth, imheight), ImageLockMode.WriteOnly, pixelformat);
IntPtr ptr = bmpData.Scan0;
Int32 psize = bmpData.Stride * imheight;
System.Runtime.InteropServices.Marshal.Copy(byteIn, 0, ptr, psize);
picOut.UnlockBits(bmpData);
return picOut;
}
And here is How image looks like;
As you can see, image is weird. First I thought if it is the camera's problem. But I have tried it with it's own program, Camera works perfectly. Something going wrong on my code.
I am giving useful informations from debug screen;
The image dimension is 3840x2748.
The size of byte array of pixel data is 10.552.320
I have made that calculation: 3840*2748 = 10.552.320 The image is not grayscale, it is RGB image,
So I Thought that pixel data includes 8-bit-indexed pixel.
I am stuck with this problem. I have tried to give you all useful information about my problem.
How can I get the image and create bitmap object correctly ?
EDIT
public Bitmap CopyDataToBitmap(int Width, int Height, byte[] data)
{
var b = new Bitmap(Width, Height, PixelFormat.Format8bppIndexed);
ColorPalette ncp = b.Palette;
int counter = 0;
for (int i = 32; i <= 256; i+=32) //for R channel (3 bit)
for (int j = 32; j <= 256; j+=32) //for G Channel (3 bit)
for (int k = 64; k <= 256; k+=64) //for B Channel (2 bit)
{
ncp.Entries[counter] = Color.FromArgb(255,i-1,j-1,k-1);
counter++;
}
b.Palette = ncp;
var BoundsRect = new Rectangle(0, 0, Width, Height);
BitmapData bmpData = b.LockBits(BoundsRect,
ImageLockMode.WriteOnly,
PixelFormat.Format8bppIndexed);
IntPtr ptr = bmpData.Scan0;
int bytes = bmpData.Stride * b.Height;
var rgbValues = new byte[bytes];
Marshal.Copy(data, 0, ptr, bytes);
b.UnlockBits(bmpData);
Console.WriteLine(b.GetPixel(3648, 1145).ToString());
return b;
}
I have changed algorithm with that function. I am using color palette. But result is still same.
ColorPalette ncp = b.Palette;
for (int i = 0; i < 257; i++)
ncp.Entries[i] = Color.FromArgb(255, i, i, i);
b.Palette = ncp;
When I use this palette, this time, image becomes Grayscale.
I just want to get clear RGB image.
EDIT 2
My camera's pixel format is BayerBG8. I dont know if it helps.