Android——自定义简化版ImageLoader

在上一篇我们已经先后介绍了 Bitmap 的高效加载方式、LruCache 以及 DiskLruCache,那么我们就动手来写一个简化版的 ImageLoader 吧!!!

一般来说,一个优秀的 ImageLoader 应该具备如下功能:

  • 图片的同步加载
  • 图片的异步加载
  • 图片的压缩
  • 内存缓存
  • 磁盘缓存
  • 网络拉取

声明一下,这里实现的 ImageLoader 并不是为了写一个框架,而是纯粹的加深下三级缓存以及图片的高效加载而写的一个小Demo。

1、图片压缩功能的实现

图片压缩在上一篇博客中已经做了介绍,这里就不在废话了,为了有良好的设计风格,这里单独抽象了一个类似于完成图片的压缩功能,这个类叫 ImageResizer,它的实现如下:

public class ImageResizer {
   
    private static final String TAG = "ImageResizer";

    public ImageResizer() {

    }

    /**
     * 根据指定的资源文件以及指定的宽/高进行等比例缩放
     * @param res
     * @param resId
     * @param reqWidth
     * @param reqHeight
     * @return
     */
    public static Bitmap decodeSampledBitmapFromResource(Resources res, int resId, int reqWidth, int reqHeight) {
        BitmapFactory.Options options = new BitmapFactory.Options();
        options.inJustDecodeBounds = true;
        BitmapFactory.decodeResource(res, resId, options);
        options.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight);
        options.inJustDecodeBounds = false;
        return BitmapFactory.decodeResource(res, resId, options);
    }

    /**
     * 根据文件流的文件描述符以及指定的宽/高进行等比例缩放
     * @param fileDescriptor
     * @param reqWidth
     * @param reqHeight
     * @return
     *
     */
    public static Bitmap decodeSampledBitmapFromFileDescriptor(FileDescriptor fileDescriptor, int reqWidth, int reqHeight) {

        BitmapFactory.Options options = new BitmapFactory.Options();
        options.inJustDecodeBounds = true;
        BitmapFactory.decodeFileDescriptor(fileDescriptor, null, options);
        options.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight);
        Log.e("00000000", reqWidth + "=====" + reqHeight + "======" + options.inSampleSize);
        options.inJustDecodeBounds = false;
        return BitmapFactory.decodeFileDescriptor(fileDescriptor, null, options);
    }

    /**
     * 根据指定的宽/高进行 2 的指数缩放
     *
     * @param options
     * @param reqWidth
     * @param reqHeight
     * @return
     */
    private static int calculateInSampleSize(BitmapFactory.Options options, int reqWidth, int reqHeight) {
        final int width = options.outWidth;
        int height = options.outHeight;
        int inSampleSize = 1;
        if (reqHeight > 0 || reqHeight > 0) {
            if (width > reqHeight && height > reqHeight) {
                final int halfWidth = width / 2;
                final int halfHeight = height / 2;
                while (halfWidth / inSampleSize >= reqWidth
                        && halfHeight / inSampleSize >= reqHeight) {
                    inSampleSize *= 2;
                }
            }
        }
        return inSampleSize;
    }
}

2、内存缓存的实现

public class MemoryCache {
    private static MemoryCache instance;
    private LruCache<String, Bitmap> mMemoryCache;

    private MemoryCache() {
        //获取当前进程的可用内存
        int maxMemory = (int) (Runtime.getRuntime().maxMemory() / 1024);
        int cacheSize = maxMemory / 8;
        mMemoryCache = new LruCache<String, Bitmap>(cacheSize) {
            @Override
            protected int sizeOf(String key, Bitmap bitmap) {
                //完成bitmap对象大小的计算
                return bitmap.getRowBytes() * bitmap.getHeight() / 1024;
            }
        };
    }

    public static MemoryCache getInstance() {
        if (instance == null) {
            synchronized (MemoryCache.class) {
                if (instance == null) {
                    instance = new MemoryCache();
                }
            }
        }
        return instance;
    }
    public void addBitmapToMemoryCache(String uri, Bitmap bitmap) {
        String key = MD5.hashKeyFormUrl(uri);
        mMemoryCache.put(key, bitmap);
    }

    public Bitmap getBitmapFromMemoryCache(String key) {
        return mMemoryCache.get(key);
    }
}

没什么好说的,略过…

3、磁盘缓存的实现

public class DiskCache {
    private static
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值