Bitmap从BitmapFactory.decodeFile(filename)返回null

时间:2011-12-09 07:24:19

标签: android

当我调用此功能时,图像视图中没有图像 bitmapFactory.decodefile(filename)显示null ..请为此提供帮助。

这是我的代码:

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;

}

15 个答案:

答案 0 :(得分:35)

嗨,它是null,因为可能是图片大小很大并且获得异常请检查您的日志并查看是否有任何错误的outofmemory位图如果是,则使用选项:

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);
  }
}

答案 1 :(得分:10)

你为什么这样做 String imageInSD =“/ sdcard / UserImages /”+ userImageName;

我想如果你得到一个.png文件,那么只是,

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

注意:同时检查您在该位置是否有Android支持的图片文件..

答案 2 :(得分:8)

这很简单:您的文件不是Android的Bitmap实现不支持的图像或图像,或者您的路径无效。


请参阅BitmapFactory.decodeFile(String file)的文档:

  

<强>返回
  得到的解码位图,如果无法解码则为null。


通常当无法解码位图时,会将某些日志打印到logcat。仔细检查它们。

答案 3 :(得分:7)

尝试添加SD卡访问权限READ_EXTERNAL_STORAGE和/或WRITE_EXTERNAL_STORAGE。 它对我有用。

答案 4 :(得分:7)

请确保在您的选项(BitmapFactory.Options)中 InJustDecodeBounds 设置为 false ,否则它将返回null。 当您只想解码文件但在代码中不再需要它时,可以将其设置为true。这样就不需要分配额外的内存。有关详细说明,请参阅here

答案 5 :(得分:2)

如果您在android 10中尝试尝试将其添加到清单中的应用程序中 <handlers> ... <add name="ExtensionlessUrlHandler-ISAPI-4.0_32bit" path="*." verb="GET,HEAD,POST,DEBUG" modules="IsapiModule" scriptProcessor="%windir%\Microsoft.NET\Framework\v4.0.30319\aspnet_isapi.dll" preCondition="classicMode,runtimeVersionv4.0,bitness32" responseBufferLimit="0" /> <add name="ExtensionlessUrlHandler-ISAPI-4.0_64bit" path="*." verb="GET,HEAD,POST,DEBUG" modules="IsapiModule" scriptProcessor="%windir%\Microsoft.NET\Framework64\v4.0.30319\aspnet_isapi.dll" preCondition="classicMode,runtimeVersionv4.0,bitness64" responseBufferLimit="0" /> <add name="ExtensionlessUrlHandler-Integrated-4.0" path="*." verb="GET,HEAD,POST,DEBUG" type="System.Web.Handlers.TransferRequestHandler" preCondition="integratedMode,runtimeVersionv4.0" responseBufferLimit="0" /> <add name="StaticFile" path="*" verb="*" modules="StaticFileModule,DefaultDocumentModule,DirectoryListingModule" resourceType="Either" requireAccess="Read" /> </handlers> ... ... <modules> ... <add name="ApplicationInitializationModule" lockItem="true" /> <add name="AspNetCoreModule" /> <add name="RewriteModule" /> <add name="ApplicationRequestRouting" /> </modules> 可能是android 10的权限问题,因为它不允许直接访问文件

答案 6 :(得分:2)

我的解决方案是在清单的Applicaiton标签中添加

Android: requestLegacyExternalStorage = "true"

答案 7 :(得分:1)

我正在构建图像处理应用程序,尝试这些方法时也返回了null。我的控制台返回的不是错误,而是这样的degub语句

D / skia:---解码器->解码返回false

这是我发现的内容,它将使所有位图都加载到整个应用程序中

1)拥有适当权限的正确文件名

2)适当缩小图像尺寸

3)如果您需要大图像,请在您的清单下显示,像这样

 <application

    android:largeHeap="true"

</application>

使用大堆并不能替代显示正确的图像大小。这是我直接从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;
}

答案 8 :(得分:0)

我错过了API级别大于22的运行时权限检查。启动Marshmellow

答案 9 :(得分:0)

BitmapFactory.decodeFile()在整个图像放置在该确切路径之前执行。当decodeFile()执行时,没有图像。所以位图返回null。通常,高像素图像需要一些额外的时间放置在它们的路径中。所以这个例外发生了。

请检查null并尝试decodeFile。

Bitmap bitmap = null;

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

答案 10 :(得分:0)

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

如果为空,则返回null

  1. 图像的文件路径错误
  2. 当android无法解码位图图像时,请检查是否可以在其他图像查看软件中查看图像。

如果以上两点在您的代码中都可以,则表示您得到的是空值,因为android渲染图像需要花费时间。

在您的代码中添加虚拟imageviewer以加快渲染过程。

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

imgPassport.setImageBitmap(bm); //此imageviewer在我的应用程序中不可见

还请确保您没有从后台线程调用方法encodeFile(dir.getAbsolutePath())

答案 11 :(得分:0)

Google文档https://developer.android.com/topic/performance/graphics/load-bitmap#java

中给出了明确的解释。

Setting the inJustDecodeBounds property to true while decoding avoids memory allocation, returning null(用于位图对象)。

根据@Jeroen VL更改 options.inJustDecodeBounds = false 解决了问题

答案 12 :(得分:0)

如果有,请删除"options.inJustDecodeBounds = true;"

  val options =  BitmapFactory.Options();
  //options.inJustDecodeBounds = true; //delete this line
  var bitmap = BitmapFactory.decodeFile(file.getAbsolutePath(), options);

答案 13 :(得分:-1)

答案 14 :(得分:-2)

在该路径中,位图可能尚未准备好。您可以在代码中添加一些延迟。例如:

Bitmap bitmap = BitmapFactory.decodeFile(imageInSD);

if (bitmap == null) {
    Thread.sleep(1000); //delay 1 second
    bitmap = BitmapFactory.decodeFile(imageInSD);
}

if (bitmap == null) {
    Thread.sleep(3000); //add another 3 seconds delay
    bitmap = BitmapFactory.decodeFile(imageInSD);
}

if (bitmap == null) {
    Thread.sleep(5000); //add another 5 seconds delay
    bitmap = BitmapFactory.decodeFile(imageInSD);
}

这样,您可以确保位图已准备好。