您的位置:首页 > 移动开发 > Android开发

2014-10-31Android学习------setContentView(View view)--------GIF动画实现

2014-11-02 13:50 585 查看
写一篇文章很辛苦啊!!!

转载请注明,联系请邮件nlp30508@qq.com

我学习Android都是结合源代码去学习,这样比较直观,非常清楚的看清效果,觉得很好,今天的学习源码是网上找的个GIF动画完美实现 源码 百度搜就知道很多下载的地方

这节学习的就是如何让一个GIF格式的文件在手机视图上显示出来,

要想做到这步

1.你需要准备好gif图片,放到drawable下面

2.你需要定义一个ImageView控件 来放置这个图片

3.在activity里面设置这个布局文件

那么问题就来了,我们前面学习的都是这样加载布局

setContentView(R.layout.main);等等这种方法,参数是一个布局文件资源索引

现在我们这里学习另外一种方式,setContentView(View view);

也就是说让我们这个界面以一种视图来加载,很显然我们就需要去定义一个View类。

我们自定义View类,我们在前面26个字母列表的实现中就说到了,想要去自己定义一个View类,必须去继承 android.view.View这个类,然后去重载

onDraw(Canvas canvas)函数就可以实现我们自定义的视图类

接下来看看代码是怎么实现的:

class CustomGifView extends View {

//构造函数

public CustomGifView(Context context) {

super(context);//首先需要去构造基类

//这里去初始化你需要的成员变量等等

}

//重载它的onDraw(Canvas canvas)函数

public void onDraw(Canvas canvas) {

//TODO 处理你想要干的事,就是你想在画布上显示什么东西,这里都可以你自己去写,去设置

}

}

}

一.这个模式很简单,下面我们要处理的就是如何去实现动态GIF图像的播放了:

要想实现动态图片,我们必须要用到一个类,Movie,这个类就是在Android中解决GIF动画非常方便的一个选择

那么如果我们知道需要这个类,怎么去创建这个 Movie类呢,那么我们需要先去看看API关于这个类的描述了

public class

Movie

extends Object

java.lang.Object
android.graphics.Movie


Summary

Public Methods
static Movie, int, int)]decodeByteArray(byte[]
data, int offset, int length)
static MoviedecodeFile(String pathName)
static MoviedecodeStream(InputStream is)
voiddraw(Canvas canvas,
float x, float y, Paint paint)
voiddraw(Canvas canvas,
float x, float y)
intduration()
intheight()
booleanisOpaque()
booleansetTime(int
relativeMilliseconds)
intwidth()

这么多public Methods方法,我们只需要看看 返回值是 Movie类型的函数就可以了

分别是下面的这几个:

1.static Movie , int, int)]decodeByteArray(byte[]
data, int offset, int length)

很明白 它将一个byte[]类型的数组转换为一个Movie对象,从哪个位置开始,解析多长

2.static Movie decodeFile(String pathName)

它从将一个文件转换成Movie类

3.static Movie decodeStream(InputStream is)

它是将一个输入流转换成Movie类,

我们可以清楚的看到我们需要去怎么样创建一个Movie类了,方法1和方法3实质差别不大,因为我们可以将 输入流转变为byte[]类型的数组

这里我们使用第三个方法来创造这个类,

1.首先我们需要定义一个成员变量:

public Movie mMovie;

2.我们来初始化这个变量:

mMovie = Movie.decodeStream(getResources().openRawResource(R.drawable.animation));

有人在这里说,你直接给出这句代码我又看不懂了,那么好吧,我们来分析下怎么把一个文件转换成输入流

其实这个很简单,都是系统自定义的函数,我们按 快捷键 /+Alt Eclipse立马会给你显示很多函数,那么我们只需要去找它的返回值就可以了,这样的语句就相当于自动生成了

那么我解释这里面用到的函数:

1.首先要找到这个文件

getResources() //
获得当前类所在的文件夹的名字 这个非常的常用,我们要获取一个文件夹下面的文件都用这个函数





Resources
android.view.View.getResources()


public
Resources getResources
()

Since:
API Level 1

Returns the resources associated with this view.

Returns

Resources object. 返回值是重点要关注的

2.找到文件之后,我们需要去打开这个文件,也就是操作这个文件,

操作文件肯定要用到open什么之类的,按快捷键
/+Alt 肯定很多

openRawResource// 你如果看到一个Raw 要想到这个文件从资源文件索引找到的 ,重要的是关注它的返回值和参数





InputStream
android.content.res.Resources.openRawResource(int
id) throws NotFoundException


public
InputStream openRawResource
(int id)

Since:
API Level 1

Open a data stream for reading a raw resource. This can only be used with resources whose value is the name of an asset files -- that is, it can be used to open drawable, sound, and raw resources; it will fail on string and color resources.

Parameters
idThe resource identifier to open, as generated by the appt tool.
Returns

InputStream Access to the resource data.

Throws
Resources.NotFoundExceptionThrows NotFoundException if the given ID does not exist.
就这样我们完成了一个Movie类的构造过程了,也就是初始化了

二.当我们构造完成了Movie类,也就是将我们的GIF图片的信息给转存到Movie中去了,接下来我们要干什么呢?

肯定就是将这个信息展示给人看对不,也就是将这个信息画到视图上对不?对的

接下来我们就需要去处理
onDraw(Canvas canvas)这个函数了

在实现一个动画的时候,我们还需要掌握一些 知识

动画一般采用帧形式播放,这就决定我们需要去考虑播放的时间,每帧播放的长度,该帧播放完了之后,需要去更新视图对不对 也就是说这些都是需要在你的函数中去设置了

获得系统时间函数:

long now = android.os.SystemClock.uptimeMillis();

帧播放的开始时间:就是从系统当前的时间开始播放

if (mMovieStart == 0) { // first time //这个变量也需要在成员变量中定义处理

mMovieStart = now;

}

开始播放之后,我们就需要设置每帧播放多长时间:

int dur = mMovie.duration();

if (dur == 0) {

dur = 1000;

}

每帧播放多长时间设置好了,我们就需要去算出该图片需要多少帧能够播放完:

int relTime = (int) ((now - mMovieStart) % dur);

然后把该帧显示出来就行了:

mMovie.setTime(relTime);

当这些设置都做完了,我们需要做的就是将这个Movie 显示到画布上去就行了,这步千万别忘记了,

mMovie.draw(canvas, 0, 0);//0.0表示图片在视图上显示的位置

显示完了,我们还要处理什么?什么呢?哈哈,视图需要更新啊,由于是动画,这帧放完了,赶紧放下帧,那么就涉及到视图的更新了,加一句代码就可以

invalidate();

至此 整个流程就清晰了,下面贴上系统的代码和展示图片:

import com.wust.gif.R;

import android.app.Activity;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Movie;
import android.os.Bundle;
import android.view.View;

public class MainActivity extends Activity {

public Movie mMovie;
public long mMovieStart;

@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(new CustomGifView(this));
}

class CustomGifView extends View {

public CustomGifView(Context context) {
super(context);
mMovie = Movie.decodeStream(getResources().openRawResource(
R.drawable.animation));

}

public void onDraw(Canvas canvas) {

long now = android.os.SystemClock.uptimeMillis();

if (mMovieStart == 0) { // first time
mMovieStart = now;
}
if (mMovie != null) {

int dur = mMovie.duration();
if (dur == 0) {
dur = 1000;
}
int relTime = (int) ((now - mMovieStart) % dur);
mMovie.setTime(relTime);
mMovie.draw(canvas, 0, 0);
invalidate();
}
}

}

}




很简单 什么布局文件都不要,只要这个类,配置到清单文件中去,然后运行就可以,当前你的drawable下面必须有这个GIF图片
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐