需求:

近段时间正好有一个需求,是要实现Gif图只加载播放一次,并且要在Gif播放完毕后回调给系统的需求。

因为Glide 3系列的API与4系列还是有很大差距的,这里我们针对Glide 3.x和Glide 4.x的分别进行实现方案的说明。

解决方案:

在Glide3.x的解决方案:

Glide.with(this).load("xxxurl")
.listener(new RequestListener<Integer, GlideDrawable>() { @Override
public boolean onException(Exception arg0, Integer arg1,
Target<GlideDrawable> arg2, boolean arg3) {
return false;
} @Override
public boolean onResourceReady(GlideDrawable resource,
Integer model, Target<GlideDrawable> target,
boolean isFromMemoryCache, boolean isFirstResource) {
// 计算动画时长
GifDrawable drawable = (GifDrawable) resource;
GifDecoder decoder = drawable.getDecoder();
for (int i = 0; i < drawable.getFrameCount(); i++) {
duration += decoder.getDelay(i);
}
//发送延时消息,通知动画结束
handler.sendEmptyMessageDelayed(MESSAGE_SUCCESS,
duration);
return false;
}
}) //仅仅加载一次gif动画
.into(new GlideDrawableImageViewTarget(imageview, 1));

在Glide3.x的解决方案:

在Glide4.x中,我们没法再直接获取GifDecoder对象了,原因是因为GlideDrawable不再提供这个方法了。需要采用反射的方法获取到GifDecoder变量,具体代码如下:

public static void loadOneTimeGif(Context context, Object model, final ImageView imageView, final GifListener gifListener) {
Glide.with(context).asGif().load(model).listener(new RequestListener<GifDrawable>() {
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target<GifDrawable> target, boolean isFirstResource) {
return false;
} @Override
public boolean onResourceReady(GifDrawable resource, Object model, Target<GifDrawable> target, DataSource dataSource, boolean isFirstResource) {
try {
Field gifStateField = GifDrawable.class.getDeclaredField("state");
gifStateField.setAccessible(true);
Class gifStateClass = Class.forName("com.bumptech.glide.load.resource.gif.GifDrawable$GifState");
Field gifFrameLoaderField = gifStateClass.getDeclaredField("frameLoader");
gifFrameLoaderField.setAccessible(true);
Class gifFrameLoaderClass = Class.forName("com.bumptech.glide.load.resource.gif.GifFrameLoader");
Field gifDecoderField = gifFrameLoaderClass.getDeclaredField("gifDecoder");
gifDecoderField.setAccessible(true);
Class gifDecoderClass = Class.forName("com.bumptech.glide.gifdecoder.GifDecoder");
Object gifDecoder = gifDecoderField.get(gifFrameLoaderField.get(gifStateField.get(resource)));
Method getDelayMethod = gifDecoderClass.getDeclaredMethod("getDelay", int.class);
getDelayMethod.setAccessible(true);
//设置只播放一次
resource.setLoopCount(1);
//获得总帧数
int count = resource.getFrameCount();
int delay = 0;
for (int i = 0; i < count; i++) {
//计算每一帧所需要的时间进行累加
delay += (int) getDelayMethod.invoke(gifDecoder, i);
}
imageView.postDelayed(new Runnable() {
@Override
public void run() {
if (gifListener != null) {
gifListener.gifPlayComplete();
}
}
}, delay);
} catch (NoSuchFieldException e) {
e.printStackTrace();
}catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
return false;
}
}).into(imageView);
} /**
* Gif播放完毕回调
*/
public interface GifListener {
void gifPlayComplete();
}

同时,因为采用的是反射,所以别忘了proguard-rules.pro中加上Glide的反混淆规则:

#Glide
-keep class com.bumptech.glide.** {*;}

最新文章

  1. iOS 自定义方法 - 播放GIF
  2. Stack类
  3. 关于 ArtifactTransferException: Failure to transfer
  4. trackr: An AngularJS app with a Java 8 backend – Part III
  5. linux下使用NFS挂载文件系统
  6. Rechability的简单使用
  7. 如何看懂XDEBUG+WEBGRIND?(转)
  8. PowerPoint2003/2007幻灯片常用快捷键大全
  9. SQLite基础回顾
  10. 获取元素最终的background-color
  11. Spark入门实战
  12. (原创)Python 自动化测试框架详解
  13. Sublime text使用快捷键
  14. c++ explicit 构造函数
  15. [Codeforces Round #438][Codeforces 868D. Huge Strings]
  16. Go语言类型(布尔、整型、数组、切片、map等)
  17. JDBC执行SQL语句以及Date对象和字符串之间的相互转换(关键是那张标准表)
  18. 22. pt-sift
  19. 组件化和 React
  20. Entity Framework Core

热门文章

  1. 2019/12/1 智能硬件实验室(ROS方向)
  2. PV、UV、IP、TPS、QPS、RPS等网络度量术语
  3. win10 安装 MySQL-5.7.28 记录
  4. Python小数据保存,有多少中分类?不妨看看他们的类比与推荐方案...
  5. 全新一代云服务器S6,重新定义性价比
  6. 面试官:如果 http 响应头中 ETag 值改变了,是否意味着文件内容一定已经更改
  7. [TimLinux] HTTP cookie与session技术
  8. hdu2546
  9. io流函数略解(java_input流)[二]
  10. 2019企业linux运维最需要的了解的一些硬件基础知识