分分钟学会写简单的图片加载框架

众所都知,现在的android APP基本上都存在很多图片展示模块,对于刚入门的小白来说要自己写个图片加载框架是很难的

 ,所以我今天出个简单的图片加载框架,希望看了这篇文章的小白们能够学会使用AsyncTask+DiskLruCache+LruCache,加载

 图片。好啦,闲话少说开始进入代码块.

      1.通过DiskLruCachede的open方法得到 DiskLruCachede对象第一个为图片缓存的文件,第二个为版本号,第三个传一个1就行,第四个为缓存的容量

    mDisCache = DiskLruCache.open(file, getVersion(), 1, 10 * 1024 * 1024);
   2.初始化LruCache对象.
<pre name="code" class="java">             try {
                     mDisCache = DiskLruCache.open(file, getVersion(), 1, 10 * 1024 * 1024);
                     Log.e("TAG","filed "+file.getAbsolutePath());
                 } catch (IOException e) {
                     e.printStackTrace();
                 }

 
 

     3.获取app的缓存路径和版本号.

     

 /**
     * 获取缓存路径
     * @param uniName 文件名
     * @return 返回路径
     */
     private static  String getCacheDir(String uniName){
      String cache = "";
      if(Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())){
          cache =  Environment.getDownloadCacheDirectory().getAbsolutePath();
      }
         cache = context.getCacheDir().getAbsolutePath();
      return cache+ File.separator+uniName;
     }

    /**
     * 获取app的版本号
     * @return
     */
    private static  int getVersion(){
        int version = 1 ;
        PackageManager packageManager = context.getPackageManager();
        try {
            PackageInfo packageInfo = packageManager.getPackageInfo("com.huangdi.pictureframework", PackageManager.COMPONENT_ENABLED_STATE_DEFAULT);
            version = packageInfo.versionCode;
        } catch (PackageManager.NameNotFoundException e) {
            e.printStackTrace();
        }
        return version;
    }

    4.DiskLruCache的中其他两个需要使用的方法为    

     

<span style="white-space:pre">	</span>DiskLruCache.Snapshot snapshot;
            try {
                snapshot = mDisCache.get(paramsms);
                if(snapshot==null){
                  DiskLruCache.Editor edit = mDisCache.edit(paramsms);
                 if(edit!=null){
                    //请求网络下载图片
                    OutputStream outputStream = edit.newOutputStream(0);
                    if(downImageWithUrl(params[0],outputStream)){
                        edit.commit();
                    }else{
                        edit.abort();
                    }

                 }

                }
                //下载完后在次获取图片流
                snapshot = mDisCache.get(paramsms);
                if(snapshot!=null){
                    fileInputStream = (FileInputStream) snapshot.getInputStream(0);
                    fieds = fileInputStream.getFD();
                }
                Bitmap bitmap = null;
                if(fieds!=null){
                    //从路径中得图片
                    bitmap = BitmapFactory.decodeFileDescriptor(fieds);
                }
                //将图片保存到LruCache中
                if(bitmap!=null){
                    if(mLruCache.get(paramsms)==null){
                     mLruCache.put(paramsms,bitmap);
                    }
                }


  5.全部代码如下:

   

package com.huangdi.pictureframework.pirturesLoader;

import android.content.Context;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.AsyncTask;
import android.os.Environment;
import android.util.Log;
import android.util.LruCache;
import android.widget.AbsListView;
import android.widget.ImageView;

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileDescriptor;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.HashSet;
import java.util.Set;

/**
 * Created by huangdi on 15/8/18.
 */
public class ImageLoaderUtils {

     private ImageLoaderUtils(){};
     private static ImageLoaderUtils imageLoaderUtils;
     private static Context context;
    //声明一个任务集合
     private Set<LoadTasks> tasks = new HashSet<LoadTasks>();
    //传入的listview或者gridview用来获取当前tag对应的ImageViewe
     private static  AbsListView mListView;
     //声明Lru
     private static LruCache<String ,Bitmap> mLruCache;
    //声明硬盘缓存对象
     private static  DiskLruCache mDisCache;
     public  static ImageLoaderUtils getInstance(Context mContext,String uniName,AbsListView listView) {
         if (imageLoaderUtils == null) {
             synchronized (ImageLoaderUtils.class) {
                 context = mContext;
                 imageLoaderUtils = new ImageLoaderUtils();
                 mListView = listView;
                 long size = Runtime.getRuntime().maxMemory() / 8;
                 String cacheDir = getCacheDir(uniName);
                 File file = new File(cacheDir);
                 if (!file.exists()) {
                     file.mkdir();
                 }
                 try {
                     mDisCache = DiskLruCache.open(file, getVersion(), 1, 10 * 1024 * 1024);
                     Log.e("TAG","filed "+file.getAbsolutePath());
                 } catch (IOException e) {
                     e.printStackTrace();
                 }
                 ;
                 mLruCache = new LruCache<String ,Bitmap>((int) size){
                     @Override
                     protected int sizeOf(String key, Bitmap value) {
                         return value.getByteCount();
                     }
                 };
             }
         }
             return imageLoaderUtils;
     }

    /**
     * 获取缓存路径
     * @param uniName 文件名
     * @return 返回路径
     */
     private static  String getCacheDir(String uniName){
      String cache = "";
      if(Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())){
          cache =  Environment.getDownloadCacheDirectory().getAbsolutePath();
      }
         cache = context.getCacheDir().getAbsolutePath();
      return cache+ File.separator+uniName;
     }

    /**
     * 获取app的版本号
     * @return
     */
    private static  int getVersion(){
        int version = 1 ;
        PackageManager packageManager = context.getPackageManager();
        try {
            PackageInfo packageInfo = packageManager.getPackageInfo("com.huangdi.pictureframework", PackageManager.COMPONENT_ENABLED_STATE_DEFAULT);
            version = packageInfo.versionCode;
        } catch (PackageManager.NameNotFoundException e) {
            e.printStackTrace();
        }
        return version;
    }
    private ImageView imges;
    public void loadImageByUrl(String url,ImageView imgeview){
        Bitmap bitmap = mLruCache.get(Md5(url));
        imges = imgeview;
        if(bitmap==null){//说明lru没有
        //那么得去硬盘加载如果硬盘也没有的话那就去网络请求
        LoadTasks loadtask = new LoadTasks();
        loadtask.execute(url) ;
        tasks.add(loadtask);
        }else{
       if(bitmap!=null&&imgeview!=null){
           Log.e("TAG","执行有");
           imgeview.setImageBitmap(bitmap);
       }
        }
    }
    class LoadTasks extends AsyncTask<String,Void,Bitmap>{
        private FileInputStream fileInputStream;
        private FileDescriptor fieds;
        private String str;
        @Override
        protected Bitmap doInBackground(String... params) {
            String paramsms =Md5(params[0]);
            str = params[0];
            DiskLruCache.Snapshot snapshot;
            try {
                snapshot = mDisCache.get(paramsms);
                if(snapshot==null){
                  DiskLruCache.Editor edit = mDisCache.edit(paramsms);
                 if(edit!=null){
                    //请求网络下载图片
                    OutputStream outputStream = edit.newOutputStream(0);
                    if(downImageWithUrl(params[0],outputStream)){
                        edit.commit();
                    }else{
                        edit.abort();
                    }

                 }

                }
                //下载完后在次获取图片流
                snapshot = mDisCache.get(paramsms);
                if(snapshot!=null){
                    fileInputStream = (FileInputStream) snapshot.getInputStream(0);
                    fieds = fileInputStream.getFD();
                }
                Bitmap bitmap = null;
                if(fieds!=null){
                    //从路径中得图片
                    bitmap = BitmapFactory.decodeFileDescriptor(fieds);
                }
                //将图片保存到LruCache中
                if(bitmap!=null){
                    if(mLruCache.get(paramsms)==null){
                     mLruCache.put(paramsms,bitmap);
                    }
                }
                return bitmap;
            } catch (IOException e) {
                e.printStackTrace();
            }finally {
                if(fieds !=null&&fileInputStream!=null ){
                    try {
                        fileInputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
            return null;
        }

        @Override
        protected void onPostExecute(Bitmap bitmap) {
            super.onPostExecute(bitmap);
            ImageView imageView = null;
            if(mListView!=null){
             imageView = (ImageView) mListView.findViewWithTag(str);
            }
            if(imageView!=null&&bitmap!=null){
                imageView.setImageBitmap(bitmap);
            }
            tasks.remove(this);
        }
    }
    //下载图片<span style="white-space:pre">		</span>
    private boolean  downImageWithUrl(String param, OutputStream outputStream) {
        HttpURLConnection httpUrl = null;
        URL url = null;
        BufferedInputStream bis =null;
        BufferedOutputStream bos= null;
        try {
            url = new URL(param);
            httpUrl = (HttpURLConnection) url.openConnection();
            bis = new BufferedInputStream(httpUrl.getInputStream(),10*1024);
            bos = new BufferedOutputStream(outputStream,8*1024);
            int b ;
            while((b = bis.read())!=-1){
            bos.write(b);
            }
            return true;
        } catch (MalformedURLException e) {
            e.printStackTrace();
        } catch (IOException e) {
            httpUrl.disconnect();
            e.printStackTrace();
        }finally {
            try {
                if(bis!=null){
                    bis.close();
                }
                if(bos!=null){
                    bos.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return false;
    }

    private String Md5(String str){
        String newsUrl;
        try {
            MessageDigest messageDigest = MessageDigest.getInstance("MD5");
            messageDigest.update(str.getBytes());
            newsUrl = bytesToHexString(messageDigest.digest());
        } catch (NoSuchAlgorithmException e) {
            newsUrl = String.valueOf(str.hashCode());
            e.printStackTrace();

        }
        return  newsUrl;
    }
    private String bytesToHexString(byte[] bytes) {
        StringBuilder sb = new StringBuilder();
        for (int i = 0; i < bytes.length; i++) {
            String hex = Integer.toHexString(0xFF & bytes[i]);
            if (hex.length() == 1) {
                sb.append('0');
            }
            sb.append(hex);
        }
        return sb.toString();
    }
}

   总结:该加载框架的原理为首先我们需要从内存中加载图片,先从LruCache中拿图片如果没有那么就开启一个后台任务去下载或者从DisLruCache中下载  如果硬盘里面也没有的话那么将向网络请求。通过DiskLruCache中拿到写入流将其写入硬盘中.拿到图片后需要将其放入LruCache中.最后通过url 拿到 AbsListView中指定的ImgeView并展示图片


评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值