今天做项目,发现需要显示一张超大图片,处理过后,还有561Kb
加载的时候,就crash --- OOM
shortMsg:java.lang.OutOfMemoryError
longMsg:java.lang.OutOfMemoryError: bitmap size exceeds VM budget
stackTrace:java.lang.OutOfMemoryError: bitmap size exceeds VM budget
at android.graphics.Bitmap.nativeCreate(Native Method)
at android.graphics.Bitmap.createBitmap(Bitmap.java:477)
at android.graphics.Bitmap.createBitmap(Bitmap.java:444)
at android.graphics.Bitmap.createScaledBitmap(Bitmap.java:349)
at android.graphics.BitmapFactory.finishDecode(BitmapFactory.java:512)
at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:487)
at android.graphics.BitmapFactory.decodeResourceStream(BitmapFactory.java:336)
代码如下:
detailView=(ImageView)findViewById(R.id.detailView);
detailView.setBackgroundResource(R.drawable.more_info);//this line will lead to OOM
换成这种:
detailView.setImageResource(R.drawable.more_info); //也同样会OOM
后来找到了solution:
/**
* 以最省内存的方式读取本地资源的图片
* @param context
*@param resId
* @return
*/
public static Bitmap readBitMap(Context context, int resId){
BitmapFactory.Options opt = new BitmapFactory.Options();
opt.inPreferredConfig = Bitmap.Config.RGB_565;
opt.inPurgeable = true;
opt.inInputShareable = true;
//获取资源图片
InputStream is = context.getResources().openRawResource(resId);
return BitmapFactory.decodeStream(is,null,opt);
}
取得bitmap之后,再 detailView.setImageBitmap(pdfImage); 就ok了!
那是为什么,会导致oom呢:
原来当使用像 imageView.setBackgroundResource,imageView.setImageResource, 或者 BitmapFactory.decodeResource 这样的方法来设置一张大图片的时候,
这些函数在完成decode后,最终都是通过java层的createBitmap来完成的,需要消耗更多内存。
因此,改用先通过BitmapFactory.decodeStream方法,创建出一个bitmap,再将其设为ImageView的 source,decodeStream最大的秘密在于其直接调用JNI>>nativeDecodeAsset()来完成decode,无需再使用java层的createBitmap,从而节省了java层的空间。如果在读取时加上图片的Config参数,可以跟有效减少加载的内存,从而跟有效阻止抛out of Memory异常。
另外,需要特别注意:
decodeStream是直接读取图片资料的字节码了, 不会根据机器的各种分辨率来自动适应,使用了decodeStream之后,需要在hdpi和mdpi,ldpi中配置相应的图片资源,否则在不同分辨率机器上都是同样大小(像素点数量),显示出来的大小就不对了。
原文引用:http://blog.csdn.net/woshicaixianfeng/article/details/6825295
分享到:
相关推荐
"Android加载网络图片与本地图片解决OOM问题"这个主题旨在介绍如何有效地解决这些问题。 首先,我们需要理解为什么Android应用容易出现OOM。Android为每个应用程序分配了一定量的内存,当这个限制被超过时,系统会...
本篇文章将详细讲解如何在Android中加载大图以避免OOM问题,参考自博客《Android加载大图避免OOM》。 1. OOM概述 OOM是Java虚拟机在分配内存时遇到的问题,当应用程序请求的内存超过系统可分配的阈值,系统无法...
"Android高级应用源码-加载本地图片,绝对不会出现OOM.zip"是一个针对这一问题的解决方案,它包含了如何在Android应用中加载本地图片而不引发内存溢出的示例代码。 首先,我们要理解为什么加载图片会引发OOM。在...
在 Android 开发中,加载大图片是一个常见的问题,这可能会引发 OOM(Out of Memory)异常。OOM 异常是指应用程序试图分配超过系统可用内存的内存空间,从而导致应用程序崩溃。为了解决这个问题,开发者需要了解 ...
在加载图片时,如果一次性加载所有图片到内存中,特别是高分辨率的图片,会迅速消耗大量内存,从而引发OOM。 针对这个问题,我们可以采取以下策略: 1. **使用低分辨率的缩略图**:加载原图前,先将其压缩为适合...
这个"Android加载本地图片,绝对不会出现OOM"的项目是一个毕业设计示例,旨在教会开发者如何在Android环境中有效地加载图片,避免内存管理问题。以下是对该项目中涉及的知识点的详细解释: 1. **图片加载库**:...
以上就是避免Android应用在加载本地图片时出现OOM的关键点。通过合理的图片处理和内存管理,我们可以确保应用在处理大量图片时仍能保持流畅运行。同时,使用成熟的图片加载库,如Glide或Picasso,可以进一步简化代码...
在Android应用开发中,图片加载是一项关键任务,尤其是在处理大量图片或者进行滑动浏览时,如果处理不当,可能会导致内存溢出(Out Of Memory,简称OOM)。"Android-Universal-Image-Loader-master"是一个非常实用的...
在加载图片时,先调用`BitmapTool.decodeSampledBitmapFromResource`方法,然后设置到`ImageView`: ```java Bitmap bitmap = BitmapTool.decodeSampledBitmapFromResource(getResources(), R.drawable.large_...
内存缓存是一种高速缓存,当图片被加载后,会被暂存到内存中,下次再次请求同一图片时,可以直接从内存中获取,减少I/O操作。然而,内存资源有限,因此当内存不足时,会根据LRU(Least Recently Used)算法进行清理...
这个压缩包“Android应用源码之加载本地图片,绝对不会出现OOM.zip”显然是一个关于如何在Android中正确加载图片以避免内存溢出的示例代码。这里我们将详细讨论如何在Android应用中安全、高效地加载本地图片,并避免...
"安卓Android源码——加载本地图片,绝对不会出现OOM.zip"这个压缩包文件显然是针对如何避免在Android应用中加载图片时出现内存溢出提供的一种解决方案。下面将详细讲解这个话题。 1. 图片加载引发的OOM问题: 当...
在Android开发中,由于系统对每个应用程序分配的内存有限,加载大尺寸的图片可能会导致“Out Of Memory”(OOM)异常,从而影响应用的稳定性和性能。为了解决这个问题,我们需要掌握一些有效的策略来优化图片加载,...
本篇文章将深入探讨如何使用LRUCache来解决Android图片墙中的OOM问题。 一、Android OOM简介 当应用程序请求的内存超过系统分配的最大内存时,就会发生OOM。在Android中,每个应用都有自己的Dalvik虚拟机实例,其...
首先,我们需要理解为什么Android加载大图会引发OOM。Android系统为每个应用分配了一定量的内存,当加载大图片时,如果图片尺寸超过可用内存,就会导致内存溢出。因此,加载图片时必须进行适当的缩放和处理。 1. ...
有效控制了Android大图片、多图片加载的OOM异常。
综上所述,解决Android加载图片出现的OOM问题需要综合运用各种策略,包括优化图片加载、缓存管理、使用合适的图片库以及合理地管理生命周期。只有这样,才能在保证用户体验的同时,避免因图片处理引发的内存问题。