Android图片三级缓存开发
因为目前工程无法使用第三方,只能搞一个三级缓存了三级缓存分为内存缓存,本地缓存,网络缓存;缓存的步骤依次是网络,内存,本地,然后取的顺序为内存,本地,网络。在加载图片时引用时尽量采用弱引用避免出现图片过多产生OOM.。
1、内存缓存,android为我们提供LruCache=其中维护着一个LinkedHashMap。LruCache可以用来存储各种类型的数据,我们设置它的大小,一般是系统最大存储空间的1/8.
publicclassMemoryCacheUtil{
privateLruCachelruCache;
publicMemoryCacheUtil(){
intmaxSize=(int)(Runtime.getRuntime().maxMemory()/8);
//一般获取当前应用的最大内存的1/8作为LruCache的容量
lruCache=newLruCache(maxSize){
//设置当前添加的图片的大小
@Override
protectedintsizeOf(Stringkey,Bitmapvalue){
returnvalue.getRowBytes()*value.getHeight();
}
};
}
//从内存缓存取图片
publicBitmapgetBitmap(Stringurl){
returnlruCache.get(url);
}
//在内存缓存存图片
publicvoidputBitmap(Stringurl,Bitmapbitmap){
lruCache.put(url,bitmap);
}
}
2、本地缓存根据url,获取本地文件,把url进行md5加密,作为文件名,保证文件的正确性.
MD5加密工具类
publicclassMD5Encoder{
publicstaticStringencode(Stringstring)throwsException{
byte[]hash=MessageDigest.getInstance("MD5").digest(string.getBytes("UTF-8"));
StringBuilderhex=newStringBuilder(hash.length*2);
for(byteb:hash){
if((b&0xFF)<0x10){
hex.append("0");
}
hex.append(Integer.toHexString(b&0xFF));
}
returnhex.toString();
}
}
本地缓存
publicclassLocalCacheUtil{
privateStringCACHE_URl;
privateMemoryCacheUtilmemoryCacheUtil;
publicLocalCacheUtil(MemoryCacheUtilmemoryCacheUtil){
//初始化本地存储的路径
CACHE_URl=Environment.getExternalStorageDirectory().getAbsoluteFile()+"/test";
this.memoryCacheUtil=memoryCacheUtil;
}
//从本地sdcard取图片
publicBitmapgetBitmap(Stringurl){
//根据url,获取本地文件,把url进行md5加密,作为文件名
try{
StringfileName=MD5Encoder.encode(url);
Filefile=newFile(CACHE_URl,fileName);
if(file.exists()){//判断当前文件是否存在
//把当前文件转换成Bitmap对象
Bitmapbitmap=BitmapFactory.decodeFile(file.getAbsolutePath());
//需往内存中存一份
memoryCacheUtil.putBitmap(url,bitmap);
returnbitmap;
}
}catch(Exceptione){
e.printStackTrace();
}
returnnull;
}
//往本地存图片的方法
publicvoidsaveBitmap(Stringurl,Bitmapbitmap){
try{
StringfileName=MD5Encoder.encode(url);
Filefile=newFile(CACHE_URl,fileName);
//判断是否需要创建父目录
FileparentFile=file.getParentFile();
if(!parentFile.exists()){
parentFile.mkdirs();
}
//把Bitmap对象保存到文件中质量越高压缩速度越慢
OutputStreamstream=newFileOutputStream(file);
bitmap.compress(CompressFormat.PNG,100,stream);//第一个参数可以设置图片格式,第二个图片压缩质量,第三个为图片输出流
}catch(Exceptione){
e.printStackTrace();
}
}
}
3、网络缓存使用异步加载AsyncTask,使用其有二种原因:
1.doInBackground运行在子线程,做网络请求耗时操作,避免主线程堵塞;
2.onPreExecute和onPostExecute便于更新UI提高用户体验。
publicclassNetCacheUtil{
privateMemoryCacheUtilmemoryCacheUtil;
privateLocalCacheUtillocalCacheUtil;
privateListViewlv_image_list;
publicNetCacheUtil(MemoryCacheUtilmemoryCacheUtil,LocalCacheUtillocalCacheUtil){
this.memoryCacheUtil=memoryCacheUtil;
this.localCacheUtil=localCacheUtil;
}
publicvoiddisplay(ImageViewimageView,Stringurl,ListViewlv_image_list){
this.lv_image_list=lv_image_list;
newMyAsyncTask(imageView).execute(newObject[]{url,imageView});
}
classMyAsyncTaskextendsAsyncTask
4、封装三级缓存形成ImageUtil,因内存缓存中取速度较快,所以先从内存缓存中取,取不到->本地缓存中取,取不到->网络缓存中取。
publicclassImageUtils{
privateMemoryCacheUtilmemoryCacheUtil;
privateLocalCacheUtillocalCacheUtil;
privateNetCacheUtilnetCacheUtil;
publicImageUtils(){
memoryCacheUtil=newMemoryCacheUtil();
localCacheUtil=newLocalCacheUtil(memoryCacheUtil);
netCacheUtil=newNetCacheUtil(memoryCacheUtil,localCacheUtil);
}
publicvoiddisplay(ImageViewimageView,Stringurl,ListViewlv_photo_list){
Bitmapbitmap=null;
/**
*因内存缓存中取速度较快
*内存缓存中取,取不到->本地缓存中取,取不到->网络缓存中取
*/
bitmap=memoryCacheUtil.getBitmap(url);//从内存缓存取图片
if(bitmap!=null){
imageView.setImageBitmap(bitmap);
return;
}
bitmap=localCacheUtil.getBitmap(url);//从本地缓存取图片
if(bitmap!=null){
imageView.setImageBitmap(bitmap);
return;
}
//开启线程访问网络,下载图片,并且展示
netCacheUtil.display(imageView,url,lv_photo_list);
}
}
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持毛票票。
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。