Picaso完美兼容OkHttp3.3,缓存优化两不误 - Tamic Developer"s Blog
为何在Fresco,Glide这么强大的背景下,我又想起了当初的Picasso,又为何写这篇文章?是因为最近项目采用了square公司的RxAndroid,Retrfit和OKhttp, 不得不联想到这个公司曾经还有款图片加载Picasso,所以采用了square公司的全家桶来进行项目开发,为了减少开发成本和也防止Apk增大,毕竟一个公司的框架之前兼容性不用担心,那么请让我们回顾一下Picass之路
首先先让我们看看主流图片加载库
Picasso,Square公司的开源项目 ,和Square的网络库一起能发挥最大作用。占用内存小,自身不带缓存,需依赖OKhttps实现缓存,不支持gif图片
Fresco,FB的明星项目,也是2015最火的项目之一,匿名共享缓存等机制保证低端机表现极佳,但是源代码基于C/C++,阅读困难度提升。效率高,sdk库占用包体积比较大
Glide,Google员工私人项目,但是Google很多项目在用,占用内存小,减低oom更靠谱,相对Picasso在Gif方面有优势,并自带缓存功能!
我做了一个实验对比 用一个普通listview加载50张图片,并快速滑动列表,下面分别是glide和picasso消耗内存图
分析后得出 一个占用内存大 一个占用cpu资源大, 这种区别是由于picasso只缓存一张大图,每次加载根据imagview的大小裁剪,因此消耗的cpu资源高,glide是分别存储不同尺寸的小图,每次不用计算,因此消耗内存比较多,加载速度相对Picasso也快,但也很耗流量.
为了避免OOM, 我毫不犹豫选择了消耗内存较小的picasso, Fresco不用说都是加载速度第一的框架,采用c库 ,我没做集成测试,具体消耗多少cpu资源我无法给出数据,据说业界第一,但是对apk大小要求的项目很可能不太合适,这里对Apk包体积要求不高的项目,Fresco是优先的首选。
喜欢glide的朋友可以看看这篇文章 :http://mrfu.me/2016/02/27/Glide_Getting_Started/
实验测试并做了简单比较后,为何还要继续说Picasso,不是说他有多快多流畅,只是当你使用了square公司其他的开源项目,会发现他们都会依赖okhttp,okhttp的强大不言而喻,一个网络库可以无缝隙的对接Retrofit和Picasso.今天只介绍piacsso相关的,说说picasso(官方:https://github.com/square/picasso) 的一些常用技巧!
#使用方式:
配置gradle
dependencies {
c
compile 'com.squareup.picasso:picasso:2.5.2'
compile 'com.squareup.okhttp3:okhttp:3.3.1'
compile 'com.squareup.okhttp3:logging-interceptor:3.3.1'
}
据说目前的2.5.3已修复了2.52无法兼容okhttp3
的问题,但我还是选择了2.52版本。
基本加载用法
Picasso.with(getApplication())
.load(url)
.into(imageView);
以上用法很简单,加载图片时提供url插入到imageview即可,picasso
其他强大功还没有太多的理解的同学请Follow Me!
#裁剪图片
|
|
这句方法会出现bug,误用!
请用Transformation
来进行转义实现:
|
|
Transformation可以拦截到picasoo返回的bitmap
,拿着bitmap随心所欲!
|
|
列如处理圆形头像
|
|
接着设置渲染模式
|
|
清空缓存
新的版本2.52 已经无法直接拿到之前的cache,因此可以用Picasso.invalidate()的实现清楚缓存!
以前我们可以这样
|
|
但现在 不行了
稍加封装成了这样子:
|
|
当然也可以这样!
|
|
在加载图片时直接不让做缓存!
加入缓存
当然2.5.2没做对oKhttp3.3的兼容,因此我们加入自定义的cilent,对okhttp做下缓存定制,请照着下面姿势作
构建OkHttpClient
|
|
拦截器Interceptor
拦截器大家都不陌生,尤其是玩过okhttp和retofit的朋友,那肯定是拦截http的拦截请求和响应的.
public class CaheInterceptor implements Interceptor {
private Context context;
public CaheInterceptor(@NonNull Context context) {
this.context = context;
}
@Override
public Response intercept(Chain chain) throws IOException {
Request request = chain.request();
if (NetworkUtil.isNetworkAvailable(context)) {
Response response = chain.proceed(request);
// read from cache for 60 s
int maxAge = 300;
String cacheControl = request.cacheControl().toString();
Log.e("Tamic", maxAge+ "s load cahe:" + cacheControl);
return response.newBuilder()
.removeHeader("Pragma")
.removeHeader("Cache-Control")
.header("Cache-Control", "public, max-age=" + maxAge)
.build();
} else {
Log.e("Tamic", " no network load cahe");
request = request.newBuilder()
.cacheControl(CacheControl.FORCE_CACHE)
.build();
Response response = chain.proceed(request);
//set cahe times is 3 days
int maxStale = 60 * 60 * 24 * 3;
return response.newBuilder()
.removeHeader("Pragma")
.removeHeader("Cache-Control")
.header("Cache-Control", "public, only-if-cached, max-stale=" + maxStale)
.build();
}
}
}
添加到Picasso中
|
|
自定义DownLoader
为了兼容okhttp3.31 实现下载器!
public class ImageDownLoader implements Downloader {
OkHttpClient client = null;
public ImageDownLoader(OkHttpClient client) {
this.client = client;
}
@Override
public Response load(Uri uri, int networkPolicy) throws IOException {
CacheControl cacheControl = null;
if (networkPolicy != 0) {
if (NetworkPolicy.isOfflineOnly(networkPolicy)) {
cacheControl = CacheControl.FORCE_CACHE;
} else {
CacheControl.Builder builder = new CacheControl.Builder();
if (!NetworkPolicy.shouldReadFromDiskCache(networkPolicy)) {
builder.noCache();
}
if (!NetworkPolicy.shouldWriteToDiskCache(networkPolicy)) {
builder.noStore();
}
cacheControl = builder.build();
}
}
Request.Builder builder = new Request.Builder().url(uri.toString());
if (cacheControl != null) {
builder.cacheControl(cacheControl);
}
okhttp3.Response response = client.newCall(builder.build()).execute();
int responseCode = response.code();
if (responseCode >= 300) {
response.body().close();
throw 大专栏 Picaso完美兼容OkHttp3.3,缓存优化两不误 - Tamic Developer"s Blognew ResponseException(responseCode + " " + response.message(), networkPolicy,
responseCode);
}
boolean fromCache = response.cacheResponse() != null;
ResponseBody responseBody = response.body();
return new Response(responseBody.byteStream(), fromCache, responseBody.contentLength());
}
@Override
public void shutdown() {
Cache cache = client.cache();
if (cache != null) {
try {
cache.close();
} catch (IOException ignored) {
}
}
}
}
接着将ImageDownLoader 加入到Picasso
|
|
这样我们在做图片加载时 就可以:
|
|
因此用了Picasso我们可以直接将缓存策略用到retrofit上去,其实一箭双雕,大大简化了开发成本!
#如何支持Https
姿势很简单 利用上面构建好的downloader
, 设置OkHttp
的protocols
即可,并构建ssl。
|
|
优化相关
优化不缓存策略
|
|
降低内存消耗
设置RGB_565编码格式,降低内存消耗
|
|
取消加载
|
|
还有很多api,比如:
requestCreator.tag(tag);设置key
requestCreator.error(); 设置加载失败图片
mPicasso.pauseTag(); 暂停加载
mPicasso.resumeTag();恢复加载
mPicasso.cancelRequest();取消加载
requestCreator.priority()优先级
- requestCreator..rotate() 旋转之类
下面说几个常用的api
#扩展加载
当然还有一个对通知栏加载的api
通知栏支持
|
|
widget支持
|
|
第一个是远程视图,第二个view Id 第三个是widget的id数组
预加载
有返回值
|
|
此api可以预先加载图片到disk和内存中,并有返回值Bitmap,此api必须同步调用,不能用UI主线程去调用,通常我们可以用在viewpager中预加载后面index的图片,或者提前拿到目标bitmap来进行业务操作,或者一些效果处理。
无返回值
|
|
也有预加载图片功能,此api可以在主线程调用,主要有callback实现,提供失败和成功函数供上层调用。但无法获取的加载好的图片资源。
|
|
#取消加载
- cancelRequest(ImageView imageView)
- cancelTag(Object obj)
- cancelRequest(Target)
主要以后上面的三种方式,第一个不明思议,就是取消某个view的加载请求,通常我们在activity死亡时候调用,第三个方法方法是我们取消某个指定的加载action, 譬如一次加载中设置了picasso的 Picasso.with(context).tag()时,就可以用cancelTag(”tag”)取消指定的请求,那么最后一个又是什么,他需要我们加入Tag的包装类 Target来进行回调请求处理。方便开发者上层对取消流程的控制。
|
|
另外还有一个对通知栏图片的取消的接口
|
|
通知栏的VIEW大家都非常熟悉,都是用RemoteViews 来进行转换展现的,那么在通知被cancel时我们就可以直接调用这个取消的方法
后记
总之虽然picasso 并不是最快的图片加载框架,但是他在基本的加载本地和网络图片基础上,还能很好的提供了让我们自我扩展能力,其扩展性和适应性更强,相信你结合了ohttp+ rxJava + Picasso 后你会发现他确实适合你!
如果你爱好glide请看这篇完美的文章:glide系列教程)
Picaso完美兼容OkHttp3.3,缓存优化两不误 - Tamic Developer"s Blog的更多相关文章
- Picasso 完美兼容 OkHttp3.3,缓存优化两不误
Tamic 专注移动开发!更多文章请关注http://www.jianshu.com/p/6241950f9daf csdn: http://blog.csdn.net/sk719887916/art ...
- NSCache和NSURLCache、网络缓存优化
本文目录 一种缓存优化方案 响应头'Last-Modified'和请求头'If-Modified-Since' 'Keep-Alive'响应头和不离线的URLSession 'Expires'响应头 ...
- Dapper完美兼容Oracle,执行存储过程,并返回结果集。
Dapper完美兼容Oracle,执行存储过程,并返回结果集. 这个问题,困扰了我整整两天. 刚刚用到Dapper的时候,感觉非常牛掰.特别是配合.net 4.0新特性dynamic,让我生成泛型集合 ...
- PHP服务缓存优化之ZendOpcache、xcache、eAccelerator
PHP服务缓存优化原理 Nginx 根据扩展名或者过滤规则将PHP程序请求传递给解析PHP的FCGI,也就是php-fpm进程 缓存操作码(opcode) Opcode,PHP编译后的中间文件,缓存给 ...
- Web Uploader - 功能齐全,完美兼容 IE 的上传组件
文件上传是网站和 Web 应用程序的常用功能,一直没有一款完美的文件上传组件,因此让很多开发人员碰到头疼的浏览器兼容问题. WebUploader 是由 Baidu FEX 团队开发的一款以 HTML ...
- MySQL优化二(连接优化和缓存优化)
body { font-family: Helvetica, arial, sans-serif; font-size: 14px; line-height: 1.6; padding-top: 10 ...
- MySQL优化-一 、缓存优化
body { font-family: Helvetica, arial, sans-serif; font-size: 14px; line-height: 1.6; padding-top: 10 ...
- Tomcat并发优化和缓存优化
Tomcat并发优化 1.调整连接器connector的并发处理能力 在Tomcat 配置文件 server.xml 中的 <Connector ... /> 配置中 1.参数说明 max ...
- 华硕200系主板完美兼容M.2安装Win7系统
虽然Windows 10系统的装机率正不断攀升,但经典的Windows 7依然有着大量的用户群体.特别是在我们中国, Windows 7依然是许许多多电脑用户的装机首选系统. 经久不衰的Windows ...
随机推荐
- [Algo] 280. Sort With 2 Stacks
Given an array that is initially stored in one stack, sort it with one additional stacks (total 2 st ...
- 吴裕雄--天生自然 pythonTensorFlow图形数据处理:数据集高层操作
import tempfile import tensorflow as tf # 1. 列举输入文件. # 输入数据生成的训练和测试数据. train_files = tf.train.match_ ...
- webservice SOA
------------------认证问题
- spring02-组件注册-@ComponentScan-自动扫描组件&指定扫描规则
上一篇我们讲到,讲@Bean注解标在某个方法上,那么ioc容器启动的时候就会将方法返回值放到ioc容器中 在开发中,实际上包扫描用的比较多,接下来我们会介绍两种方式一种是基于xml,一种是基于注解. ...
- 使用 try-with-resources 优雅关闭资源
桂林SEO:我们知道,在 Java 编程过程中,如果打开了外部资源(文件.数据库连接.网络连接等.redis),我们必须在这些外部资源使用完毕后,手动关闭它们. 因为外部资源不由 JVM 管理,无法享 ...
- ubuntu下pycharm的安装
打开百度,输入pycharm下载,点击下图的第二个英文链接. 进入后选择linux下的Community进行下载,而左边的Professional是要钱购买的,当然花钱的体验效果肯定会更好. 下载完成 ...
- NOIP2000提高组T1 进制转换
https://www.luogu.org/problem/P1017 题目描述 我们可以用这样的方式来表示一个十进制数: 将每个阿拉伯数字乘以一个以该数字所处位置的值减1为指数,以10为底数的幂之和 ...
- Spring Cloud服务的注册与发现(Eureka)
一.spring cloud简介 spring cloud 为开发人员提供了快速构建分布式系统的一些工具,包括配置管理.服务发现.断路器.路由.微代理.事件总线.全局锁.决策竞选.分布式会话等等.它运 ...
- Redhat6更改yum源 (转)
最近虚拟机中安装了redhat6.3企业版,自带的yum用不起来,软件都找不到. 网上搜了一下说是没付钱...,需要改下yum源.操作步骤如下: 1.切换到yum源存放目录[root@rhel6 ~] ...
- MySQL5.7安装教程(RPM)
博主本人平和谦逊,热爱学习,读者阅读过程中发现错误的地方,请帮忙指出,感激不尽 前言: 对应服务器信息: 192.168.247.53 一.MySQL安装(RPM) 1.系统环境设置: 1.1清空系统 ...