写点什么

Android 自定义 View 播放 Gif 动画,ffmpeg 音视频开发实战 6 下载

用户头像
Android架构
关注
发布于: 刚刚

public void setGifResource(int movieResourceId, OnPlayListener onPlayListener) {mOnPlayListener = onPlayListener;movie = Movie.decodeStream(getResources().openRawResource(movieResourceId));if (movie == null) {//如果 movie 为空,那么就不是 gif 文件,尝试转换为 bitmap 显示 Bitmap bitmap = BitmapFactory.decodeResource(getResources(), movieResourceId);if (bitmap != null) {setImageBitmap(bitmap);return;}}movieDuration = movie.duration() == 0 ? DEFAULT_DURATION : movie.duration();requestLayout();}


调用 requestLayout 重新计算 View 大小,并重新绘制。如果是 gif 格式则 View 宽高等于 movie 的宽高,不是则调用父类的测量方法。


@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {if (movie != null) {int movieWidth = movie.width();int movieHeight = movie.height();setMeasuredDimension(movieWidth, movieHeight);} else {super.onMeasure(widthMeasureSpec, heightMeasureSpec);}}


开始播放,其实就是调用 invalidate 从而调用 onDraw 方法就行 UI 绘制:


public void play(int counts) {this.counts = counts;reset();if (mOnPlayListener != null) {mOnPlayListener.onPlayStart();}invalidate();}


不断调用 onDraw 方法来绘制 Gif 当前时间的图片帧(同样需要判断是否是 gif 格式,不是则调用父类的绘制方法):


@Overrideprotected void onDraw(Canvas canvas) {if (movie != null) {if (!mPaused && hasStart) {drawMovieFrame(canvas);invalidateView();} else {drawMovieFrame(canvas);}} else {super.onDraw(canvas);}}/**


  • 画出 gif 帧*/private void drawMovieFrame(Canvas canvas) {movie.setTime(getCurrentFrameTime());movie.draw(canvas, 0.0f, 0.0f);}


最核心的方法就是计算当前时间需要绘制处于 movie 中的对应时间的图片帧。


private int getCurrentFrameTime() {if (movieDuration == 0)return 0;//因为有暂停,所以需要减去暂停时间 long


《Android学习笔记总结+最新移动架构视频+大厂安卓面试真题+项目实战源码讲义》
浏览器打开:qq.cn.hn/FTe 免费领取
复制代码


now = SystemClock.uptimeMillis() - dealyTime;int nowCount = (int) ((now - mMovieStart) / movieDuration);if (counts != -1 && nowCount >= counts) {hasStart = false;if (mOnPlayListener != null) {mOnPlayListener.onPlayEnd();}}int currentTime = (int) ((now - mMovieStart) % movieDuration);int percent = currentTime * 100 / movieDuration;if (mOnPlayListener != null && hasStart) {mOnPlayListener.onPlaying(percent);}return currentTime;}


暂停 Gif 播放:


public void pause() {if (movie != null && !mPaused && hasStart) {mPaused = true;invalidate();mMoviePauseTime = SystemClock.uptimeMillis();if (mOnPlayListener != null) {mOnPlayListener.onPlayPause(true);}} else {if (mOnPlayListener != null) {mOnPlayListener.onPlayPause(false);}}}


继续 Gif 播放:


if (mPaused && mMoviePauseTime > 0) {mPaused = false;dealyTime = dealyTime + SystemClock.uptimeMillis() - mMoviePauseTime;invalidate();if (mOnPlayListener != null) {mOnPlayListener.onPlayRestart();}}


经过这些处理,我们就能更好地控制 Gif 的播放流程了。下面简单看下成品图:


进阶

用户头像

Android架构

关注

还未添加个人签名 2021.10.31 加入

还未添加个人简介

评论

发布
暂无评论
Android自定义View播放Gif动画,ffmpeg音视频开发实战6下载