0

So, I need to use the byte array of my image to modify, for example... I have a 380x380 image, and I need to take 3x3 of the image and multiply with other array and thus with the entire image.

I never use byte array, so I dont know if im doing right

//Obtener byteArray de imagen
Image imageOri = Image.FromFile(Path);
var ms = new MemoryStream();
imageOri.Save(ms, System.Drawing.Imaging.ImageFormat.Jpeg);
var byteImage = ms.ToArray();

So, when I run this code, byteImage has a... List? of data, so, I dont know how to get the 3x3 of the image to make the process

9
  • An image is a byte array of pixels hard coded in a virtual matrix [width, height] where each point has the size of the bytes needed for the color. So you address the array like index = ( x * width + y ) * colorsize. I hope I've not made a mistake, it's a long time I coded such thing... But Bitmap has the method GetPixel(). What do you call "3x3 of the image" ? Commented Jul 9, 2020 at 19:46
  • 2
    Might help: stackoverflow.com/questions/17387509/… Commented Jul 9, 2020 at 19:52
  • @OlivierRogier 3x3 I mean the new sub array that i need to multiply... After multiply every possible 3x3, I will have a new array that I will export as new image...Ok, and if I suse Bitmap and the method .GetPixel(), how can I get those 3x3 for my process?? Commented Jul 9, 2020 at 20:05
  • 2
    When you call Image.Save, you are saving the file representation of the image to your memory stream. This is not going to be a byte array representing pixel data, but the .jpg file contents, including the headers and the results of the JPEG compression algorithm. Unless you are intimately familiar with how JPEG compression works, the contents of the byte array will be unusable for image processing. Commented Jul 9, 2020 at 20:12
  • I'm sorry, I don't understand what means "3x3 is a sub array" and "multiply every possible 3x3"... do you have an example of what it is ? Commented Jul 9, 2020 at 20:13

1 Answer 1

0

I would assume you want to apply a convolution filter.

To start with you probably want to use a Bitmap Rather than an image, i.e. new Bitmap(Path).

The trivial method would be to loop over each pixel, and then loop over each value in the filter and multiply/accumulate with the corresponding pixel values. Using GetPixel to get the pixel values. Note that you need to handle the borders of the image somehow, for example by skipping them. GetPixel is notoriously slow, but I would recommend using it to ensure you have the code nailed down before optimizing.

Something like this (Untested):

        var bmp = new Bitmap(@"test.bmp");
        var filter = new float[3, 3];
        var result = new Bitmap(bmp.Width - 2, bmp.Height - 2);
        for(int y = 1; y < bmp.Height-1; y++)
        {
            for (int x = 1; x < bmp.Width - 1; x++)
            {
                float r = 0;
                r += bmp.GetPixel(x-1, y-1).R * filter[0, 0];
                r += bmp.GetPixel(x  , y-1).R * filter[1, 0];
                r += bmp.GetPixel(x+1, y-1).R * filter[2, 0];
                r += bmp.GetPixel(x-1, y  ).R * filter[0, 1];
                r += bmp.GetPixel(x  , y  ).R * filter[1, 1];
                r += bmp.GetPixel(x+1, y  ).R * filter[2, 1];
                r += bmp.GetPixel(x-1, y+1).R * filter[0, 2];
                r += bmp.GetPixel(x  , y+1).R * filter[1, 2];
                r += bmp.GetPixel(x+1, y+1).R * filter[2, 2];

                // Repeat for G & B channels
                result.SetPixel(x-1, y-1, Color.FromArgb((int)r, 0, 0));
            }
        }

A more comprehensive guide can be found here.

Sign up to request clarification or add additional context in comments.

4 Comments

Using GetPixel and SetPixel to perform image processing on an entire image is unbelievably slow. It is much faster to use LockPixels to access the pixel data directly.
Yes, sorry but I'm not a good thing at explaining, but you got y point... On image 380x340, throw me the error OutOfRange when x = 338 on the line result.SetPixel(x, y, Color.FromArgb((int)r, 0, 0));
@Abion47 Yes, I mentioned that GetPixel is slow. But if the image is small, and it is not done all to often it is often fast enough. I did not want to have to explain lockPixel in addition to convolution, and the provided link shows how to do it the correct way.
@alfa Rojo, Oups, the setPixel coordinates should be offset by -1. Example has been updated.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.