Reducing Size of Bitmap

Reducing Size of Bitmap

Introduction-

Images come in all shapes and sizes. In many cases they are larger than required size for a typical application user interface. For example, the system Gallery application displays photos taken using your Android devices’s camera which are typically much higher resolution than the screen density of your device. So we have to reduce the size of the Bitmap of that image. We can reduce the size of Bitmap using BitmapFactory class.

BitmapFactory Class-

BitmapFactory class creates bitmap objects from various data source like files, stream and byte array. BitMapFactory class extends Objects class. This class provide several method to creates bitmap objects which are following:-

decodeByteArray –

Bitmap decodeByteArray (byte[] data,int offset, int length, BitMapFactory.Options option)
This method is used decode an immutable bitmap from the specified byte array.

Parameter

data
        byte  array of compressed size.
 offset
        offset  into image data for where the decoder should begin parsing.
  length
        The number of bytes beginning at offset to parse.
 options
        BitmapFactory.Options null-ok, Options that control downsampling and whether the image                should be completely decoded.

Return

 Bitmap
        The decoded bitmap or null if the image data could not be decoded,if option requested only               the  size be returned.

decodeFile-

Bitmap decodeFile (String pathName, BitmapFactory.Options options)
Decode a file path into a bitmap. If the specified file name is null, or cannot be decoded into a bitmap, the function returns null.

Parameter

 pathName
        Complete path name for the file to be decoded.
options
        BitmapFactory.Options null-ok, Options that control downsampling and whether the                      image should be completely decoded.

Return

Bitmap
        The decoded bitmap or null if the image data could not be decoded,if option requested only                the  size be returned.

decodeResource-

Bitmap decodeResource (Resource resource, int id, BitmapFactory.Options options)
This method is also used to generate bitmap object.

Parameter

resource
        The resource object containing image data.
    id
        The resource id of image data.
options
        BitmapFactory.Options null-ok, Options that control downsampling and whether the image              should be completely decoded.

Return

Bitmap
        The decoded bitmap or null if the image data could not be decoded,if option requested only                the  size be returned.

decodeStream-

Bitmap decodeStream (InputStream inputStream, Rect outPadding, BitmapFactory.Options options)
Decode an input stream into a bitmap. If the input stream is null then function returns null. The stream’s position will be where ever it was after the encoded data was read.

Parametre

inputStream
        The input stream that holds the raw data to be decoded into bitmap
outPadding
       If not null return padding rect for the bitmap if it exists otherwise set padding to [-1,-1,-1,-1]
 options
       BitmapFactory.Options null-ok, Options that control downsampling and whether the                   image  should be completely decoded.

Return

Bitmap         The decoded bitmap or null if the image data could not be decoded,if option requested                         only the size be returned.

Working Flow –

  1. First we create path from file object using file.getPath() and BitmapFactory. Options object and set options.inJustDecodeBounds = true.
  2. Decode image using BitmapFactory.decodeFile(filePath,options) to check dimensions. As per given in example.
  3. Calculate inSampleSize and decode again with set inSampleSize. As per given in method calculateInSampleSize(BitmapFactory.Options bmOptions) of example.

inSampleSize –

If inSampleSize > 1 requests the decoder to subsample the original image, returning a smaller image to save memory. The sample size is the number of pixels in either dimension that correspond to a single pixel in the decoded bitmap.Any value <= 1 treated as 1. The decoder uses final value based on power of 2 any other value will be rounded down to nearest power of 2. Decoder use final inSampleSize value to rounding down.

Example-

private Bitmap reduceBitmapSize(File imageFilePath)
{
    BitmapFactory.Options bmOptions = new BitmapFactory.Options();
    bmOptions.inJustDecodeBounds = true;
    BitmapFactory.decodeFile(imageFilePath.getAbsolutePath(), bmOptions);
    bmOptions.inSampleSize = calculateInSampleSize(bmOptions);
    bmOptions.inJustDecodeBounds = false;
    Bitmap bitmap =BitmapFactory.decodeFile(imageFilePath.getAbsolutePath(),bmOptions);
    return bitmap;
}
// This method is used to calculate largest inSampleSize 
//which is used to decode bitmap in required bitmap.
private int calculateInSampleSize(BitmapFactory.Options bmOptions)
{
    // Raw height and width of image
    final int photoWidth = bmOptions.outWidth;
    final int photoHeight = bmOptions.outHeight;
    int scaleFactor = 1;
    if (photoWidth > AppConstant.TARGET_IMAGE_WIDTH 
        || photoHeight > AppConstant.TARGET_IMAGE_HEIGHT)
    {
        final int halfPhotoWidth = photoWidth / 2;
        final int halfPhotoHeight = photoHeight / 2;

   // Calculate the largest inSampleSize value that is a power of 2
   //and keeps both height and width larger than the requested height and width.
        while ((halfPhotoWidth / scaleFactor) >= AppConstant.TARGET_IMAGE_WIDTH 
                && (halfPhotoHeight / scaleFactor) >= AppConstant.TARGET_IMAGE_HEIGHT)
        {
            scaleFactor *= 2;
        }
    }

    return scaleFactor;
}

 

Leave a Reply