http://blog.csdn.net/guolin_blog/article/details/11100315
The general idea is this
Powerimageview class Inherits ImageView class
Add a custom attribute to the Powerimageview class Auto_play
<Relativelayoutxmlns:android= "Http://schemas.android.com/apk/res/android"Android:layout_width= "Match_parent"Android:layout_height= "Match_parent" > <Com.example.customview.CounterViewAndroid:layout_width= "100DP"Android:layout_height= "100DP"android:layout_centerinparent= "true" /> </Relativelayout>
Constructor, initialize:
Get the resource ID, get the stream by ID, and determine if the GIF is not a picture
If it is a GIF picture, you need to get: auto_play, image length, image width these three properties
PublicPowerimageview (context context, AttributeSet attrs,intDefstyle) { Super(context, attrs, Defstyle); TypedArray a=context.obtainstyledattributes (Attrs, R.styleable.powerimageview); intResourceId =Getresourceid (A, context, attrs); if(ResourceId! = 0) { //when the resource ID is not equal to 0 o'clock, go to the stream for that resourceInputStream is =getresources (). Openrawresource (ResourceId); //decoding using the movie class convectionMmovie =Movie.decodestream (IS); if(Mmovie! =NULL) { //if the return value is not equal to NULL, it is a GIF picture, below gets whether the property is automatically playedIsautoplay = A.getboolean (R.styleable.powerimageview_auto_play,false); Bitmap Bitmap=Bitmapfactory.decodestream (IS); Mimagewidth=bitmap.getwidth (); Mimageheight=bitmap.getheight (); Bitmap.recycle (); if(!Isautoplay) { //when AutoPlay is not allowed, get the picture that starts the play button and register the click eventMstartbutton =Bitmapfactory.decoderesource (Getresources (), r.drawable.start_play); Setonclicklistener ( This); } } } }
There are two ways to get a resource ID:
1. Reflection
/*** Through Java reflection, gets the ID of the specified image resource to SRC. * * @paramA *@paramContext *@paramAttrs *@returnreturns the ID of the specified picture resource in the layout file and returns 0 without specifying any picture resources. */ Private intGetresourceid (TypedArray A, context context, AttributeSet attrs) {Try{Field field= TypedArray.class. Getdeclaredfield ("Mvalue"); Field.setaccessible (true); Typedvalue Typedvalueobject=(Typedvalue) Field.get (a); returnTypedvalueobject.resourceid; } Catch(Exception e) {e.printstacktrace (); } finally { if(A! =NULL) {a.recycle (); } } return0; }
This method can get more than just the custom attributes, all the properties that are set for ImageView can be obtained together.
2. By means of attr
for (int
{
If
{
System.out.println (Attrs.getattributeresourcevalue (i, 0) + "=========");
return attrs.getattributeresourcevalue (i, 0);
}
}
Ways to play GIF:
Save the start time to determine if the current time-start time is greater than the animation length,
Let's take a look at how the GIF image is played in the Playmovie () method. As you can see, the first time the animation starts is recorded, then the duration of the animation is recorded, and then use the current time minus the start time of the animation, the time is the Powerimageview should be displayed in the frame, and then the use of the movie object to draw this frame to the screen. Each call to the Playmovie () method then draws a frame of the picture, which, in a coherent form, forms an animated GIF. Note that this method has a return value, if the current time minus the animation start time is greater than the animation duration, it means that the animation playback is complete, return true, otherwise return false.
/*** start to play GIF animation, playback complete return true, not complete return false. * * @paramCanvas *@returnplayback Complete Returns TRUE, FALSE returns not completed. */ Private BooleanPlaymovie (canvas canvas) {Longnow =Systemclock.uptimemillis (); if(Mmoviestart = = 0) {Mmoviestart=Now ; } intDuration =mmovie.duration (); if(Duration = = 0) {Duration= 1000; } intReltime = (int) ((Now-mmoviestart)%duration); Mmovie.settime (Reltime); Mmovie.draw (Canvas,0, 0); if((Now-mmoviestart) >=duration) {Mmoviestart= 0; return true; } return false; }
To draw a GIF:
ONMEASURE Specifies the size of the image, GIF is setmeasureddimension given size
@Override protected void onmeasure (intint heightmeasurespec) { super. Onmeasure ( Widthmeasurespec, Heightmeasurespec); if NULL { // If it is a GIF picture, override the size of the set Powerimageview setmeasureddimension (Mimagewidth, mimageheight); } }
OnDraw draw pictures, non-GIR are used by default
Draw Start button at start
IsPlaying continues to call Play_movie, and then invalidate ()
@Overrideprotected voidOnDraw (canvas canvas) {if(Mmovie = =NULL) { //Mmovie is equal to NULL, stating that it is a normal picture, call the parent class's OnDraw () method directly Super. OnDraw (canvas); } Else { //Mmovie Not equal to NULL, description is a GIF picture if(isautoplay) {//If AutoPlay is allowed, call the Playmovie () method to play the GIF animationPlaymovie (canvas); Invalidate (); } Else { //when AutoPlay is not allowed, determine if the current picture is playing if(isplaying) {//continue calling the Playmovie () method until the end of the animation playback if(Playmovie (canvas)) {isplaying=false; } invalidate (); } Else { //you haven't started. Just draw the first frame of the GIF picture and draw a Start buttonMmovie.settime (0); Mmovie.draw (Canvas,0, 0); intOFFSETW = (Mimagewidth-mstartbutton.getwidth ())/2; intOffseth = (Mimageheight-mstartbutton.getheight ())/2; Canvas.drawbitmap (Mstartbutton, OFFSETW, Offseth,NULL); } } } }
We can then also modify the code in the Activity_main.xml to give it the properties that allow AutoPlay, as shown in the following code:
<Relativelayoutxmlns:android= "Http://schemas.android.com/apk/res/android"xmlns:attr= "Http://schemas.android.com/apk/res/com.example.powerimageviewtest"Android:layout_width= "Match_parent"Android:layout_height= "Match_parent" > <Com.example.powerimageviewtest.PowerImageViewAndroid:id= "@+id/image_view"Android:layout_width= "Wrap_content"Android:layout_height= "Wrap_content"android:layout_centerinparent= "true"android:src= "@drawable/anim"Attr:auto_play= "true" /> </Relativelayout>
Attention:
There is no way to set the size of the GIF, how large the GIF is, and how big it is to display it. This is mainly a demonstration of custom view, not specifically for GIF functionality
SOURCE download, please click here
android-Custom View implementation ImageView play GIF