Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it possible to reduce the size of an image comes from byte array

I have a byte array that contains a jpeg image. I was just wondering if it is possible to reduce its size?

Edit: Ok. I acknowledged my mistake. Then my question is how can I reduce the quality of the image comes from a byte array.

like image 299
Cute Bear Avatar asked Feb 24 '12 13:02

Cute Bear


People also ask

How is an image stored in a byte array?

Any image is merely a sequence of bytes structured in accordance with whatever underlying format used to represent it, eg color data, layers, dimensions, etc. The significance of any byte(s) you see during debugging is entirely dependent upon the native format of the image, eg PNG, TIFF, JPEG, BMP, etc.

What is image byte array?

Images are binary data - this is easily represented as byte arrays. The image in the sample is stored in the database as a BLOB - not a string or location, that is, it is binary data.

How big can a byte array be?

The results show the maximum size is 2,147,483,645. The same behavior can be observed for byte, boolean, long, and other data types in the array, and the results are the same.


2 Answers

Please understand that there is no free lunch. Decreasing the size of a JPEG image by increasing the compression will also decrease the quality of the image. However, that said, you can reduce the size of a JPEG image using the Image class. This code assumes that inputBytes contains the original image.

var jpegQuality = 50; 
Image image; 
using (var inputStream = new MemoryStream(inputBytes)) {
  image = Image.FromStream(inputStream);
  var jpegEncoder = ImageCodecInfo.GetImageDecoders() 
    .First(c => c.FormatID == ImageFormat.Jpeg.Guid); 
  var encoderParameters = new EncoderParameters(1); 
  encoderParameters.Param[0] = new EncoderParameter(Encoder.Quality, jpegQuality); 
  Byte[] outputBytes; 
  using (var outputStream = new MemoryStream()) { 
    image.Save(outputStream, jpegEncoder, encoderParameters);
    outputBytes = outputStream.ToArray(); 
  } 
}

Now outputBytes contains a recompressed version of the image using a different JPEG quality.

By decreasing the jpegQuality (should be in the range 0-100) you can increase the compression at the cost of lower image quality. See the Encoder.Quality field for more information.

Here is an example where you can see how jpegQuality affects the image quality. It is the same photo compressed using 20, 50 and 80 as the value of jpegQuality. Sizes are 4.99, 8.28 and 12.9 KB.

JPEG quality sample image

Notice how the text becomes "smudged" even when the quality is high. This is why you should avoid using JPEG for images with uniformly colored areas (images/diagrams/charts created on a computer). Use PNG instead. For photos JPEG is very suitable if you do not lower the quality too much.

like image 199
Martin Liversage Avatar answered Oct 17 '22 06:10

Martin Liversage


Please try:

// Create a thumbnail in byte array format from the image encoded in the passed byte array.  
// (RESIZE an image in a byte[] variable.)  
public static byte[] CreateThumbnail(byte[] PassedImage, int LargestSide)  
{  
    byte[] ReturnedThumbnail;  

    using (MemoryStream StartMemoryStream = new MemoryStream(),  
                        NewMemoryStream = new MemoryStream())  
    {  
        // write the string to the stream  
        StartMemoryStream.Write(PassedImage, 0, PassedImage.Length);  

        // create the start Bitmap from the MemoryStream that contains the image  
        Bitmap startBitmap = new Bitmap(StartMemoryStream);  

        // set thumbnail height and width proportional to the original image.  
        int newHeight;  
        int newWidth;  
        double HW_ratio;  
        if (startBitmap.Height > startBitmap.Width)  
        {  
            newHeight = LargestSide;  
            HW_ratio = (double)((double)LargestSide / (double)startBitmap.Height);  
            newWidth = (int)(HW_ratio * (double)startBitmap.Width);  
        }  
        else 
        {  
            newWidth = LargestSide;  
            HW_ratio = (double)((double)LargestSide / (double)startBitmap.Width);  
            newHeight = (int)(HW_ratio * (double)startBitmap.Height);  
        }  

        // create a new Bitmap with dimensions for the thumbnail.  
        Bitmap newBitmap = new Bitmap(newWidth, newHeight);  

        // Copy the image from the START Bitmap into the NEW Bitmap.  
        // This will create a thumnail size of the same image.  
        newBitmap = ResizeImage(startBitmap, newWidth, newHeight);  

        // Save this image to the specified stream in the specified format.  
        newBitmap.Save(NewMemoryStream, System.Drawing.Imaging.ImageFormat.Jpeg);  

        // Fill the byte[] for the thumbnail from the new MemoryStream.  
        ReturnedThumbnail = NewMemoryStream.ToArray();  
    }  

    // return the resized image as a string of bytes.  
    return ReturnedThumbnail;  
}  

// Resize a Bitmap  
private static Bitmap ResizeImage(Bitmap image, int width, int height)  
{  
    Bitmap resizedImage = new Bitmap(width, height);  
    using (Graphics gfx = Graphics.FromImage(resizedImage))  
    {  
        gfx.DrawImage(image, new Rectangle(0, 0, width, height),   
            new Rectangle(0, 0, image.Width, image.Height), GraphicsUnit.Pixel);  
    }  
    return resizedImage;  
}
like image 23
TechDo Avatar answered Oct 17 '22 05:10

TechDo