android gif播放卡顿,PhotoView播放gif卡顿

问题出现场景

引入github著名第三方库PhotoView

在项目的需求中有点击查看大图,查看大图里的组件用的PhotoView,并且宽高设置为match_parent,出现了比较明显的卡顿

与ImageView进行对比

ImageView宽高设置为match_parent

设置ScaleType为MATRIX(手势缩放需要的类型)

对比发现,在ImageView的setImageDrawable的时候,ImageView里的Drawable的Bounds和PhotoView里的Bounds不一致,其实追溯到源码是可以发现。Drawable的Bounds在ScaleType为MATRIX时,取的值为Drawable本身的getIntrinsicWidth和getIntrinsicHeight

如下源码

if (dwidth <= 0 || dheight <= 0 || ScaleType.FIT_XY == mScaleType) {

/* If the drawable has no intrinsic size, or we're told to

scaletofit, then we just fill our entire view.

*/

mDrawable.setBounds(0, 0, vwidth, vheight);

mDrawMatrix = null;

} else {

// We need to do the scaling ourself, so have the drawable

// use its native size.

mDrawable.setBounds(0, 0, dwidth, dheight);

…………

}

总结以下几点

那么说明加载出来的Drawable本身他的getIntrinsicWidth和getIntrinsicHeight不一致

假定Canvas绘制压力来自于加载出来的图片的像素大小(毕竟没看过源码,单单比较得出的结论)

加载出来的图片资源不一致

那么首先笔者用的是图片框架是Glide,在Glide的源码中有这样一段代码

public Target into(ImageView view) {

Util.assertMainThread();

Preconditions.checkNotNull(view);

if (!requestOptions.isTransformationSet()

&& requestOptions.isTransformationAllowed()

&& view.getScaleType() != null) {

if (requestOptions.isLocked()) {

requestOptions = requestOptions.clone();

}

switch (view.getScaleType()) {

case CENTER_CROP:

requestOptions.optionalCenterCrop();

break;

case CENTER_INSIDE:

requestOptions.optionalCenterInside();

break;

case FIT_CENTER:

case FIT_START:

case FIT_END:

requestOptions.optionalFitCenter();

break;

case FIT_XY:

requestOptions.optionalCenterInside();

break;

case CENTER:

case MATRIX:

default:

// Do nothing.

}

}

return into(context.buildImageViewTarget(view, transcodeClass));

}

会自动根据ImageView的scaleType自动进行相应的配置,想深究的可以研究下Glide源码,这里不做详细分析,回过头来再看PhotoView

PhotoView重写了getScaleType方法

@Override

public ScaleType getScaleType() {

return attacher.getScaleType();

}

PhotoViewAttacher里的mScaleType默认为FIT_CENTER

private ScaleType mScaleType = ScaleType.FIT_CENTER;

……

public ScaleType getScaleType() {

return mScaleType;

}

到此可以说明了PhotoView本身的ScaleType和提供给外界引用的ScaleType并不一致

实践

自定义一个PhotoNewView,完全copyPhoto的代码,仅在getScaleType中返回super.getScaleType()

测试得出,这样修改以后,完美达到预期,gif不再卡顿,同时Drawable承载的信息和ImageView一致

解决方案

方案一

点击看大图的时候,如果图片是GIF类型的,那么不采用PhotoView,反之,用PhotoView

方案二

如上所说,自定义一个自己需要的PhotoNewView,为了保险起见,建议多提供一个方法,来选择性提供返回View本身的ScaleType或者是PhotoViewAttacher里的mScaleType,若熟读了PhotoView的源码,也是能做更精细的扩展

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值