视频在滑动列表中的异步缓存和播放

视频在滑动列表中的异步缓存和播放,转自大量高质量游戏应用源码的众筹论坛

http://www.zccode.com/forum.php?mod=viewthread&tid=679&extra=

最近在Github上看到VideoPlayerManager这么一个项目,目的在是ListView和RecyclerView中播放小视频,模仿了Instagram中滑动到可见视频项时开始播放该视频,滑动至不可见时停止视频播放的功能

但是该项目存在几个问题:

  1. 快速上下滑动列表后,无法再播放视频,有时还会直接Crash
  2. 不支持网络视频的异步缓存

故在该项目的基础上进行了优化,并且支持网络视频的异步缓存

网络视频的异步缓存

视频的缓存其实跟图片缓存大致是一样的,现在图片缓存框架很多,但是根本原理都是网络下载+内存缓存+本地缓存这三大块组成。而视频的缓存只需要跳过内存缓存就可以了,当发视频文件未下载时就去下载并本地缓存,下次就直接从本地缓存读取视频文件信息,所以基于图片缓存框架不难实现视频文件的缓存功能。

这里我采用了Glide来实现视频缓存,Glide不仅支持图片缓存还支持对普通文件缓存,所以使用Glide可以很简单的就能实现视频文件的缓存

基于TextureView的视频播放控件

Android原生提供了一个视频播放控件 - VideoView,但VideoView是基于SurfaceView实现的,SurfaceView会单独一个窗口用来绘制,它不在View hierachy中,显示也不受View的属性控制,不能进行平移,缩放等变换,也难以放在ListView或者ScrollView中,一些View中的特性也无法使用。

为了弥补SurfaceView的不足,Android在4.0中加入了TextureView,它并没有创建一个单独的窗口用来绘制,这使得它可以像一般的View一样执行一些变换操作,设置透明度等,也很方便的放在其它ViewGroup中

所以要在ListView或者RecyclerView中播放视频,我们就需要实现基于TextureView的VideoView,实现代码参考ViewVideo就可以了

视频在滑动列表中的自动播放和停止

要实现视频的自动播放和停止,我们需要计算每个item中列表中的可见比。比如当某item可见比大于70%时,则该item视为可见的,激活视频播放。反之视为不可见,停止视频播放

这里简单说下实现原理,主要分为下面三步

  1. 在列表滑动时,判断滑动方向
  2. 根据滑动方向判断相邻的item是否视为可见,比如在下滑列表时,当前可见item的可见比在逐渐减小,而下一项的可见比在逐渐加大,当前item可见比低于70%时停止播放,下一项可见比大于70%时就开始播放
  3. 在快速滑动列表时,不检测item的变化(避免卡顿);在滑动停止时,查找当前可见item中可见比最大的item,如果该item和之前可见的item不一样时,则激活该item

列表中视频播放的性能问题

视频的播放主要使用了MediaPlayer,MediaPlayer的状态图如下所示:

state diagram

从图中可以看出,视频在开始播放前需要首先通过setDataSource()进行初始化,然后通过prepare()或者prepareAsync()进行播放前准备工作,最后准备完成后通过start()操作才开始播放视频

其中prepare()操作是相当耗时的,这一步操作绝不应该在UI线程中调用,而prepareAsync()则是使用异步的方式调用,所以在list列表中播放视频应该使用prepareAsync()来准备视频

光靠prepareAsync()这一步,可不足以保证list滑动时每帧耗时不超过16ms,像setDataSource(),reset(),release()这些操作都是比较耗时的,虽然达不到引起ANR的程度,但是对于list滑动的流畅性却影响很大

解决方案

这里我采用了将MediaPlayer的全部操作都放在一个单独的线程中去处理,事件回调则通过ui Handler post回ui线程,这样就可以保证list滑动的流畅性

效果预览

代码具体的使用和详细实现方法都已放到Github上

项目地址:VideoListPlayer

欢迎大家拍砖

原文出处:blog.waynell.com

时间: 2024-10-18 06:42:09

视频在滑动列表中的异步缓存和播放的相关文章

phpcms视频模块实现列表页打开内容页直接播放视频

摘自phpcms论坛 原链接地址:http://bbs.phpcms.cn/thread-557691-1-1.html 之前下载研究过“化蝶自在飞”开发的视频模型,发现功能不错,但唯一的缺憾是,我想在列表页打开,然后直接在内容页播放,经过“汨罗之窗”站长的点拨,本人现分享一个视频模块,仅调用 外部FLV视频 ,其他视频格式请自行找播放器代码.本人是新手,目的仅在于为新手提供便利,做的不好,请高手们不要见笑...1:新建视频模型,然后添加一个视频字段,字段类型为“单行文本”.2:字段名称“自定义

在可滑动列表(ListView & RecyclerView)中实现视频播放

Facebook: Instagram: Magisto 这篇文章里的技术是基于VideoPlayerManager这个开源类库的. 类库包含所有的代码以及一个示例.我在这篇文章里会跳过一些东西,所以如果要搞清楚某个细节,那最好还是把源码导入IDE然后再看这篇文章吧.就算你不看源码,这篇文章还是可以让你理解我以何种方式解决了什么问题. 两个问题 要实现目标我们要解决两个问题: 我们要控制视频播放.在Android系统中我们可以使用MediaPlayer.class操作SurfaceView而且播

浅谈Android中的异步加载之ListView中图片的缓存及优化三

     隔了很久没写博客,现在必须快速脉动回来.今天我还是接着上一个多线程中的异步加载系列中的最后一个使用异步加载实现ListView中的图片缓存及其优化.具体来说这次是一个综合Demo.但是个人觉得里面还算有点价值的就是里面的图片的缓存的实现.因为老实说它确实能在实际的项目中得到很好的应用.主要学习来源于慕课网中的异步加载学习,来自徐宜生大神的灵感.本次也就是对大神所讲知识的一个总结及一些个人的感受吧. 这次是一个综合的Demo,主要里面涉及到的知识主要有:网络编程.异步加载.JSON解析.

在滚动列表中实现视频的播放(ListView & RecyclerView)

英文原文:Implementing video playback in a scrolled list (ListView & RecyclerView) 本文将讲解如何在列表中实现视频播放.类似于诸如 Facebook, Instagram 或者 Magisto这些热门应用的效果: Facebook: Magisto: Instagram: 这片文章基于开源项目: VideoPlayerManager. 所有的代码和示例都在那里.本文将跳过许多东西.因此如果你要真正理解它是如何工作的,最好下载

WP8_区分滑动和点击(在图片列表中)

在windows phone中,对于一个页面中 有图片列表的,滑动的时候,很容易被误认为是点击了图片,而打开图片详细信息等,原意是滑动列表,由此对图片添加2个事件,来控制其点击行为(滑动的时候,基本不会执行到do clicked something处)   private bool _isClickEnable = false; private DateTime _clickedTime;   private void Img1_OnMouseLeftButtonDown(object send

Android在滚动列表中实现视频的播放 ListView RecyclerView

英文原文:Implementing video playback in a scrolled list (ListView & RecyclerView) 本文将讲解如何在列表中实现视频播放.类似于诸如 Facebook, Instagram 或者 Magisto这些热门应用的效果: Facebook: Magisto: Instagram: 这片文章基于开源项目: VideoPlayerManager. 所有的代码和示例都在那里.本文将跳过许多东西.因此如果你要真正理解它是如何工作的,最好下载

h.264参考图像列表、解码图像缓存

1.参考图像列表(reference picture list) 一般来说,h.264会把需要编码的图像分为三种类型:I.P.B,其中的B.P类型的图像由于采用了帧间编码的这种编码方式,而帧间编码又是以参考图像为基础进行的,因此需要有个参考图像列表来管理之前生成的参考图像,方便用于对当前图像进行编码. 2.解码图像缓存(decoded picture buffer) 随着图像编码的进行,(解码阶段)会不断有新的图像生成(重建图像),已解码图像会被放到解码图像缓存区中(或直接输出,这个在下面DPB

《Linux4.0设备驱动开发详解》笔记--第九章:Linux设备驱动中的异步通知与同步I/O

在设备驱动中使用异步通知可以使得对设备的访问可进行时,由驱动主动通知应用程序进行访问.因此,使用无阻塞I/O的应用程序无需轮询设备是否可访问,而阻塞访问也可以被类似"中断"的异步通知所取代.异步通知类似于硬件上的"中断"概念,比较准确的称谓是"信号驱动的异步I/O". 9.1 异步通知的概念和作用 异步通知:一旦设备就绪,则主动通知应用程序,该应用程序无需查询设备状态 几种通知方式比较: 阻塞I/O :一直等待设备可访问后开始访问 非阻塞I/O:

集群环境中使用 EhCache 缓存系统

EhCache 缓存系统 : 本章节将要介绍EhCache及EhCache实现分布式的一些解决方案.并针对于这些解决性方案做一个实现,后续将出一个提供项目模块化.服务化.插件化的VieMall快速开发平台,同时集成Dubbo服务化.Zookeeper(分布式调度/分布式配置管理服务).Redis分布式缓存技术及Memcache/Ehcache 二级缓存切换.FastDFS分布式文件系统.ActiveMQ异步消息中间件.Solr搜索.Nginx负载均衡等分布式及读写分离.如果有时间可以深入分表分库