关于引用本地资源图片 造成OOM的解决方案

情景

在实际开发中,我们会常常使用到本地的UI,这些是固定功能的导航索引,例如一个GridView的导航界面。
最近的一个项目就出现了这样的情况,在不使用第三方图片框架的情况下,解决这个问题.

解决方案:


  1. BitmapFactory.decodeStream(InputStream, null, BitmapFactory.Options);

原先我们使用的ImageView.setBackgroundResource/setImageResource , 这些方法,都会使用Java层的createBitmap来创建一个Bitmap,意味着会消耗更多内存。
BitmapFactory.decodeStream,则是直接调用JNI nativeDecodeAsset(),而不再通过Java层,从而节省了Java层的内存空间,有效地防止了OOM的异常。
    public static Bitmap getBitmapFromRecource(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);
        }

2.出现OOM的原因之一是使用过多资源,没有及时释放.

在当前Activity中,将使用到底Bitmap对象,存储到一个集合中,在该Activity销毁的时候,释放这些资源。

所以,我们可以重载该方法,List的创建:只有当你需要引用到多个ResourceDrawable的时候.

/**
     * 根据ResourceId获取Bitmap对象,并插入到Bitmap集合中;
     * 
     * @param context
     * @param bitmapList
     * @param resId
     * @return
     */
 public static Bitmap getBitmapFromRecource(Context context, List<Bitmap> bitmapList, 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);
        Bitmap bitmap = BitmapFactory.decodeStream(is, null, opt);
        insertBitmap(bitmapList, bitmap);
        return bitmap;
    }

/**
     * 将当前的Bitmap插入到List中
     * 
     * @param bitmapList
     * @param bitmap
     * @return
     */
    private static void insertBitmap(List<Bitmap> bitmapList, Bitmap bitmap) {
        if (!bitmapList.contains(bitmap)) {
            bitmapList.add(bitmap);
        }
    }

3.最后,在Activity销毁的时候,要对所有当前Activity使用到的Bitmap进行回收.

/**
     * 当不再使用到的时候,回收所有的Bitmap
     * 
     * @param bitmapList
     */
    public static void recycleBitmapUnuseful(List<Bitmap> bitmapList) {
        if (null != bitmapList && 0 != bitmapList.size()) {
            for (Bitmap bitmap : bitmapList) {
                bitmap.recycle();
            }
            bitmapList.clear();
            bitmapList = null;
        }
    }


@Override
    protected void onDestroy() {
        recycleBitmapUnuseful(bitmapList);
        super.onDestroy();
    }

本文仅限于学习交流,不足之处,请踊跃指出,欢迎来喷.

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值