45

When I am calling this function there is no image in image view bitmapFactory.decodefile(filename) showing null .. please help for this.

Here is my code :

public Bitmap ShowImage(String imageName,String userImageName ) 
{

    File sdcard_mainDirectory = new File(Environment.getExternalStorageDirectory(),"UserImages").getAbsoluteFile();

    File file = new File(sdcard_mainDirectory, userImageName).getAbsoluteFile();

    if (file != null) {

        try {

            String imageInSD = "/sdcard/UserImages/"+userImageName;

            Bitmap bitmap = BitmapFactory.decodeFile(imageInSD);

            return bitmap;

        }
        catch (Exception e) {

            e.printStackTrace();
        }

    }

    return null;

}
mac
  • 42,153
  • 26
  • 121
  • 131
Sumit Patel
  • 2,547
  • 8
  • 33
  • 45

14 Answers14

44

Hi it is null because may be the image size is big and getting exception please check your log and see is there any error of outofmemory bitmap if yes then use options for that:

BitmapFactory.Options options;

try {
  String imageInSD = "/sdcard/UserImages/" + userImageName;
  Bitmap bitmap = BitmapFactory.decodeFile(imageInSD);
  return bitmap;
} catch (OutOfMemoryError e) {
  try {
    options = new BitmapFactory.Options();
    options.inSampleSize = 2;
    Bitmap bitmap = BitmapFactory.decodeFile(imageInSD, null, options);
    return bitmap;
  } catch(Exception excepetion) {
    Log.e(excepetion);
  }
}
pRaNaY
  • 24,642
  • 24
  • 96
  • 146
kalpana c
  • 2,739
  • 3
  • 27
  • 47
  • 1
    still getting null and empty as I'm using this method https://stackoverflow.com/a/28425042/3388029 – Prasad Mar 16 '18 at 12:57
  • @kalpana c Great suggestion to check the logs; I found my error (different one than what you posted) because of that. Thank you! – shagberg Feb 06 '22 at 21:46
  • first of all you can't access files like this directly in android 10 and above. second it doesn't matter the image size if you have enabled largeheap = true – Khalid Ahmad Fazli Feb 22 '22 at 11:09
  • 1
    @AnooshKhalid true. Since this issue has reported in 2011 and the response is also too old. that time android 10 was not available. I agreed now it has changed a lot. Thanks for your reply. – kalpana c Mar 24 '22 at 06:50
14

Why are you doing this String imageInSD = "/sdcard/UserImages/"+userImageName;

I think If you get a .png file is present then just,

 Bitmap bitmap = BitmapFactory.decodeFile(file.getAbsolutePath());

NOTE: Also check you have a Android supported image file is present in that location..

user370305
  • 108,599
  • 23
  • 164
  • 151
  • 1
    When loading cached images from external storage, file.getAbsolutePath() fixed it for me, even though the getPath() was correct. – scottyab Feb 19 '13 at 16:05
12

Be sure that in your options (BitmapFactory.Options) the InJustDecodeBounds is set to false or otherwise it will return null. This can be set to true when you just want the file to be decoded but you don't need it further in your code. This way no extra memory needs to be allocated. See here for more explanation.

Jeroen VL
  • 341
  • 5
  • 9
  • Can you elaborate what do you mean by `This can be set to true when you just want the file to be decoded but you don't need it further in your code.`. I need the Bitmap coming from `BitmapFactory.decodeFile` and call `compress(Bitmap.CompressFormat.PNG, 50, byteArrayOutputStream)`. Will it be just fine after setting this in `BitmapFactory.Options`? – Bitwise DEVS Jul 04 '22 at 20:13
  • 1
    If you set "InJustDecodeBounds" as "True" then the Bitmap that is returned from "BitmapFactory.decodeFile" method will always be null. If you want to use the Bitmap that is returned from the "decodeFile" method then you have to set the "InJustDecodeBounds" property of the options to "False". In short: in your case you have to set it to "False" because you want to use it afterwards in your "compress" method. – Jeroen VL Jul 06 '22 at 06:41
11

It's simple: your file either is not an image or image that is not supported by Android's Bitmap implementation, or you path is invalid.


See documentation for BitmapFactory.decodeFile(String file):

Returns
the resulting decoded bitmap, or null if it could not be decoded.


Usually when bitmap cannot be decoded some logs are printed to logcat. Inspect them carefully.

inazaruk
  • 74,247
  • 24
  • 188
  • 156
9

Try to add SD card access permissions READ_EXTERNAL_STORAGE and/or WRITE_EXTERNAL_STORAGE. It works for me.

eyal
  • 2,379
  • 7
  • 40
  • 54
8

if you are trying in android 10 try adding this to your application in manifest android:requestLegacyExternalStorage="true" it may be a permission issue with android 10 since it doesn't allow direct access to files

4

I was missing run time permission check on API level greater than 22. Starting Marshmellow

abitcode
  • 1,420
  • 17
  • 24
mallaudin
  • 4,744
  • 3
  • 36
  • 68
3

My solution was to add the below-mentioned property in the manifest's Application tag:

Android:requestLegacyExternalStorage = "true"
Vishal Naikawadi
  • 419
  • 6
  • 11
2

The BitmapFactory.decodeFile() executes before the entire image placing in that exact path. When decodeFile() executes there is no image. So the bitmap returns null. Generally the high pixel images takes some extra time to place in their path. So this exception happens.

Please check the null and try to decodeFile.

Bitmap bitmap = null;

while(bitmap == null)
   bitmap = BitmapFactory.decodeFile(imageInSD);
1

I'm building an image processing app and have also returned null when trying these methods. My console returned not an error but a degub statement like this

D/skia: --- decoder->decode returned false

Here is what I found that will get any bitmap to load throughout my application

1) correct file name with appropriate permissions

2) Scale image down when appropriate

3) If you need a large image set it under you manifest like so

 <application

    android:largeHeap="true"

</application>

Using a large heap is not a substitute for displaying the correct image size. Here is an example of the code I use directly from androids docs

 public Bitmap getRawImageThumb(Context mContext)
{
    Bitmap b = null;

    int reqHeight = 100, reqWidth = 100;

    String filename = mContext.getFilesDir().toString() + "/" + rawFileName;
    Log.d(TAG, "processRawReceipt: " + rawFileName);


    BitmapFactory.Options options = new BitmapFactory.Options();
    options.inJustDecodeBounds = true;
    //options.inPreferredConfig = Bitmap.Config.ARGB_8888;
    BitmapFactory.decodeFile(filename, options);
    int height = options.outHeight;
    int width = options.outWidth;


    int inSampleSize = 1;

    if (height > reqHeight || width > reqWidth) {

        final int halfHeight = height / 2;
        final int halfWidth = width / 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 ((halfHeight / inSampleSize) >= reqHeight
                && (halfWidth / inSampleSize) >= reqWidth) {
            inSampleSize *= 2;
        }
    }

    options.inSampleSize = inSampleSize;
    options.inJustDecodeBounds = false;
    Log.d(TAG, "getRawImage: " + String.valueOf(height) + " "  + String.valueOf(width) + " " + String.valueOf(inSampleSize));
    b = BitmapFactory.decodeFile(filename, options);

    return b;
}
cagney
  • 492
  • 3
  • 11
  • When `inJustDecodeBounds` is used as an option when `BitmapFactory.decodeFile(filepath, options)` is called. Please note, it will only change the options `OutWidth` and `OutHeight` and the bitmap returned is null. – Pierre Feb 04 '19 at 11:21
0
Bitmap bitmap = BitmapFactory.decodeFile(file.getAbsolutePath());

This returns null, if

  1. File paths to the image is wrong
  2. when android cannot decode the bitmap image, so check if you can view the image in other image view software.

if the above two point are okay in your code, it means you are getting a null value because its taken time for android to render the image.

add a dummy imageviewer in your code to speed up the render process.

bm=BitmapFactory.decodeFile(dir.getAbsolutePath());

imgPassport.setImageBitmap(bm); // This imageviewer is not visible in my App

Also ensure you are not calling the method decodeFile(dir.getAbsolutePath()) from background thread

UYI EKE
  • 11
  • 2
0

A clear explanation is given in google documentation https://developer.android.com/topic/performance/graphics/load-bitmap#java

Setting the inJustDecodeBounds property to true while decoding avoids memory allocation, returning null for the bitmap object.

as per @Jeroen VL changing options.inJustDecodeBounds = false solved the problem

creativecoder
  • 1,470
  • 1
  • 14
  • 23
0

Delete "options.inJustDecodeBounds = true;" if you have

  val options =  BitmapFactory.Options();
  //options.inJustDecodeBounds = true; //delete this line
  var bitmap = BitmapFactory.decodeFile(file.getAbsolutePath(), options);
Ribaz
  • 476
  • 3
  • 10
-1

Try this code it will help you to solve your problem

Replace gallery image with gallery image in android show too large exception

Rao Jilani
  • 11
  • 2