I'm trying to show an animated gif. By the way I开发者_开发问答'm doing it with the class Movie. But the Android Developer page dont grant info about the methods.
How can I make the gif to be resized to fit the layout?
Thanks in advance
I've been trying to do the same thing (to display animated GIF) using this method.
It works only if you specify uses-sdk android:minSdkVersion="3"
For scaling ...
package com.example.GIFShow;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Movie;
import android.graphics.Rect;
import android.util.Log;
import android.view.View;
class MYGIFView extends View {
private static final boolean twigDebug = true;
private Movie mMovie;
private long mMovieStart;
MYGIFView(Context aContext, Movie aMovie) {
super(aContext);
if (aMovie == null)
return;
mMovie = aMovie;
mMovieStart = android.os.SystemClock.uptimeMillis();
}
protected void onDraw(Canvas aCanvas) {
super.onDraw(aCanvas);
if (mMovie == null || mMovie.duration() == 0)
return;
int relTime = (int)((android.os.SystemClock.uptimeMillis() - mMovieStart)
% mMovie.duration());
mMovie.setTime(relTime);
Bitmap movieBitmap = Bitmap.createBitmap(mMovie.width(), mMovie.height(),
Bitmap.Config.ARGB_8888);
Canvas movieCanvas = new Canvas(movieBitmap);
mMovie.draw(movieCanvas, 0, 0);
Rect src = new Rect(0, 0, mMovie.width(), mMovie.height());
Rect dst = new Rect(0, 0, this.getWidth(), this.getHeight());
aCanvas.drawBitmap(movieBitmap, src, dst, null);
this.invalidate();
}
}
Now you can get and pass a Movie object to the class in one of two ways ...
Get input GIF Movie object from project drawable folder
Movie movie = Movie.decodeStream
(context.getResources().openRawResource(R.drawable.somefile));
Or get input GIF Movie object from external storage (/mnt/sdcard ... /mnt/extSdCard ... etc)
Movie movie = null;
try {
FileInputStream stream =
new FileInputStream(Environment.getExternalStorageDirectory() +
"/somefolder/somefile.gif");
try {
byte[] byteStream = streamToBytes(stream);
movie = Movie.decodeByteArray(byteStream, 0, byteStream.length);
}
finally {
stream.close();
}
}
catch (IOException e) { }
Now set the moving GIF image / Movie object into your activity view:
View view = new MYGIFView(this, movie);
setContentView(view);
If you get the GIF image / Movie object from external storage (second example) you'll need the supporting routine:
private byte[] streamToBytes(InputStream is) {
ByteArrayOutputStream os = new ByteArrayOutputStream(1024);
byte[] buffer = new byte[1024];
int len;
try {
while ((len = is.read(buffer)) >= 0)
os.write(buffer, 0, len);
}
catch (java.io.IOException e) { }
return os.toByteArray();
}
You answer is good. It helped me alot.I have changed one thing for performance .Moved the bitmap creation to outside of ondraw
import java.io.InputStream;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Movie;
import android.graphics.Rect;
import android.os.SystemClock;
import android.util.AttributeSet;
import android.view.View;
public class GifView extends View {
private Movie mMovie;
InputStream mStream;
long mMoviestart;
private Context context;
public GifView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
this.context = context;
init();
}
public GifView(Context context, AttributeSet attrs) {
super(context, attrs);
this.context = context;
init();
}
public GifView(Context context) {
super(context);
this.context = context;
init();
}
Bitmap movieBitmap = null;
private void init() {
InputStream object = this.getResources().openRawResource(
R.raw.postloadinganimation);
mMovie = Movie.decodeStream(object);// context.getResources().getAssets().open("PostLoadingAnimation.gif"));
movieBitmap = Bitmap.createBitmap(mMovie.width(),
mMovie.height(), Bitmap.Config.ARGB_8888);
}
@Override
protected void onDraw(Canvas canvas) {
canvas.drawColor(Color.TRANSPARENT);
super.onDraw(canvas);
final long now = SystemClock.uptimeMillis();
if (mMoviestart == 0) {
mMoviestart = now;
}
final int relTime = (int) ((now - mMoviestart) % mMovie.duration());
mMovie.setTime(relTime);
// mMovie.draw(canvas, 0, 0);
Canvas movieCanvas = new Canvas(movieBitmap);
mMovie.draw(movieCanvas, 0, 0);
Rect src = new Rect(0, 0, mMovie.width(), mMovie.height());
Rect dst = new Rect(0, 0, this.getWidth(), this.getHeight());
canvas.drawBitmap(movieBitmap, src, dst, null);
this.invalidate();
}
}
I know, this is very old post.
But you can try this ...
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
if (mMovie != null) {
int movieWidth = mMovie.width();
int movieHeight = mMovie.height();
/** Calculate horizontal scaling*/
float scaleH = 1f;
int measureModeWidth = MeasureSpec.getMode(widthMeasureSpec);
if (measureModeWidth != MeasureSpec.UNSPECIFIED) {
int maximumWidth = MeasureSpec.getSize(widthMeasureSpec);
if (movieWidth > maximumWidth) {
scaleH = (float) movieWidth / (float) maximumWidth;
}else{
scaleH = (float) maximumWidth / (float) movieWidth;
}
}
/** calculate vertical scaling*/
float scaleW = 1f;
int measureModeHeight = MeasureSpec.getMode(heightMeasureSpec);
if (measureModeHeight != MeasureSpec.UNSPECIFIED) {
int maximumHeight = MeasureSpec.getSize(heightMeasureSpec);
if (movieHeight > maximumHeight) {
scaleW = (float) movieHeight / (float) maximumHeight;
}else{
scaleW = (float) maximumHeight / (float) movieHeight;
}
}
/** calculate overall scale*/
mScale = Math.max(scaleH, scaleW);
mMeasuredMovieWidth = (int) (movieWidth * mScale);
mMeasuredMovieHeight = (int) (movieHeight * mScale);
setMeasuredDimension(widthMeasureSpec, heightMeasureSpec);
} else {
/*No movie set, just set minimum available size.*/
setMeasuredDimension(getSuggestedMinimumWidth(), getSuggestedMinimumHeight());
}
}
private void drawMovieFrame(Canvas canvas) {
mMovie.setTime(mCurrentAnimationTime);
canvas.save(Canvas.MATRIX_SAVE_FLAG);
canvas.scale(mScale, mScale);
mLeft = (getWidth() - mMeasuredMovieWidth) / 2f;
mTop = (getHeight() - mMeasuredMovieHeight) / 2f;
mMovie.draw(canvas, mLeft / mScale, mTop / mScale);
canvas.restore();
}
精彩评论