日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

分析android动画模块[转]

發布時間:2023/12/9 编程问答 35 豆豆
生活随笔 收集整理的這篇文章主要介紹了 分析android动画模块[转] 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

2019獨角獸企業重金招聘Python工程師標準>>>

作者: 劉鵬 日期: 2009-03-07 Android 平臺提供了兩類動畫,一類是 Tween 動畫,即通過對場景里的對象不斷做圖像變換(平移、縮放、旋轉)產生動畫效果;第二類是 Frame 動畫,即順序播放事先做好的圖像,跟電影類似。本文分析了 Tween 動畫的實現原理。

主要思路

Tween 動畫通過對 View 的內容完成一系列的圖形變換 (包括平移、縮放、旋轉、改變透明度)來實現動畫效果。

具體來講,預先定義一組指令,這些指令指定了圖形變換的類型、觸發時間、持續時間。這些指令可以是以 XML 文件方式定義,也可以是以源代碼方式定義。程序沿著時間線執行這些指令就可以實現動畫效果。

動畫的進度使用 Interpolator 控制,android 提供了幾個 Interpolator 子類,實現了不同的速度曲線,如LinearInterpolator 實現了勻速效果、 Accelerateinterpolator 實現了加速效果、DecelerateInterpolator 實現了減速效果等。還可以定義自己的 Interpolator 子類,實現拋物線、自由落體等物理效果。

動畫的運行模式有兩種:

  • 獨占模式,即程序主線程進入一個循環,根據動畫指令不斷刷新屏幕,直到動畫結束;
  • 中斷模式,即有單獨一個線程對時間計數,每隔一定的時間向主線程發通知,主線程接到通知后更新屏幕;

圖形變換通過仿射矩陣實現。圖形變換是圖形學中的基本知識。簡單來說就是,每種變換都是一次矩陣運算。在 Android 中,Canvas 類中包含當前矩陣,當調用 Canvas.drawBitmap (bmp, x, y, Paint) 繪制時,android 會先把 bmp 做一次矩陣運算,然后將運算的結果顯示在 Canvas 上。這樣,編程人員只需不斷修改 Canvas 的矩陣并刷新屏幕,View 里的對象就會不停的做圖形變換,動畫就形成了。

在 android 中提供了 Animation 、 Interpolator、Transformation 等類具體實現 Tween 動畫,下面逐一分析。

Animation 類及其子類

Animation 類及其子類是動畫的核心模塊,它實現了各種動畫效果,如平移、縮放、旋轉、改變透明度等。

Tween 動畫的每一楨都根據 Interpolator 對 view 的內容做一次圖形變換,因此 Animation 的核心工作是做變換(transformation)。

Aniamtion 是基類,他記錄了動畫的通用屬性和方法。主要的屬性包括動畫持續時間、重復次數、interpolator 等。動畫里最重要的方法是 getTransformation (currentTime, outTransformation),該方法根據當前間 (currentTime) 和 interpolator,計算當前的變換,在 outTransformation 中返回。

TranslateAnimation、RotateAnimation、AlphaAnimation 等是 Animation 的子類,分別實現了平移、旋轉、改變 Alpha 值等動畫。

每個動畫都重載了父類的 applyTransformation 方法,這個方法會被父類的 getTransformation 方法調用。另外每個動畫還有個 initialize 方法,完成初始化工作。

不同的動畫具有不同的屬性,如 RotateAnimation 的屬性是起始角度、終止角度和旋轉點坐標, TranslateAnimation 的屬性是起始位置和終止位置。AlphaAnimation 的屬性是起始 alpha 值和終止 alpha 值。

Animation 類及其子類的類圖如下所示:

android類及其子類

Interpolator 類及其子類

Interpolator 定義了動畫的變化速度,可以實現勻速、正加速、負加速、無規則變加速等;

Interpolator 是基類,封裝了所有 Interpolator 的共同方法,它只有一個方法,即 getInterpolation (float input),該方法 maps a point on the timeline to a multiplier to be applied to the transformations of an animation.

LinearInerpolator、AccelerateInterpolator, DecelerateInterpolator, AccelerateDecelerateInterpolator,CycleInterpolator 是 Interpolator 的子類,分別實現了勻速、加速、減速、變速、循環等效果。

對于 LinearInterpolator ,變化率是個常數,即 f (x) = x.

public float getInterpolation(float input) {return input;}

對于 AccelerateInterpolator,開始變化很慢,然后逐漸變快,即 f(x) = x*x 或者 f(x) = pow(x, 2*mFactor).

public float getInterpolation(float input) {if (mFactor == 1.0f) {return (float)(input * input);} else {return (float)Math.pow(input, 2 * mFactor);}}

對于 AccelerateDecelerateInterpolator,變化率開始和結束都很慢,但中間很快,即 f(x) = (cos ((x+1)*PI) / 2.0f) + 0.5f.

public float getInterpolation(float input) {return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;}

Interpolator 類及其子類的類圖如下所示:

Interpolator 類及其子類

Transformation 類

Transformation 記錄了仿射矩陣 Matrix,動畫每觸發一次,會對原來的矩陣做一次運算, View 的 Bitmap 與這個矩陣相乘就可實現相應的操作(旋轉、平移、縮放等)。

Transformation 類封裝了矩陣和 alpha 值,它有兩個重要的成員,一是 mMatrix,二是 mAlpha。

Transformation 類圖如下所示:

Transformation 類圖

如何在 View 中實現動畫

從邏輯上講,實現動畫需要如下幾步:

  • view 創建動畫對象,設置動畫屬性,調用 invalidate 刷新屏幕,啟動動畫;
  • invalidate 方法觸發了 onDraw 函數;
  • 在 onDraw 函數中:
    • 調用動畫的 getTransformation 方法,得到當前時間點的矩陣
    • 將該矩陣設置成 Canvas 的當前矩陣
    • 調用 canvas 的 drawBitmap 方法,繪制屏幕。
    • 判斷 getTransformation 的返回值,若為真,調用 invalidate 方法,刷新屏幕進入下一楨;若為假,說明動畫完成。
  • 整個流程可用一個序列圖表示:

    Tween 動畫序列圖

    使用樣例

    下面的代碼是一個 view,系統創建 view 時會調用 onCreate 方法,該方法定義了一個 TranslateAniamtion,指定了移動起點和終點,動畫持續時間為 1s,最后調用 startAnimation 將該動畫保存在 View 的成員 mCurrentAnianmtion 中并啟動動畫。

    注意,在 View 中需要定義成員變量 mCurrentAnimation 和 mTransformation ,分別記錄當前的動畫和變換。另外需要定義成員函數 startAnimation 啟動動畫。

    class MyView extends View {

    ??? Animation mCurrentAnimation? = null;

    ??? Transformation mTransformation = new Transformation;

    ?

    ??? private void setAnimation(Animation animation) {
    ??????? mCurrentAnimation = animation;
    ??????? if (animation != null) {
    ??????????? animation.reset();
    ??????? }
    ??? }

    ?

    ??? public void startAnimation(Animation animation) {
    ??????? animation.setStartTime(animation.START_ON_FIRST_FRAME);
    ??????? setAnimation(animation);
    ??????? invalidate();
    ??? }


    ??? onDraw (Canvas canvas) {

    ??????? long curTime = SystemClock.uptimeMillis ();

    ??????? if (mCurrentAniamtion == null){

    ??????????? canvas.drawBitmap (b, x, y, mPaint);

    ??????? }

    ??????? else {

    ??????????? if (!mCurrentAnimation.isInitialized())? //initialize animation

    ??????????????? mCurrentAnimation.initialize (w, h, pw, ph);

    ??????????? boolean more = mCurrentAnimation.getTransformation (curTime, mTransformation);

    ??????????? if(more) {

    ??????????????? Matrix m = canvas.getMatrix();

    ??????????????? canvas.setMatrix (mTransformation.getMatrix());

    ??????????????? canvas.drawBitmap (b, x, y, mPaint);

    ??????????????? canvas.setMatrix (m);

    ??????????????? this.invalidate ();

    ??????????? }

    ??????????? else {

    ??????????????? mCurrentAnimation = null;

    ??????????????? this.invalidate ();

    ??????????? }

    ??????? }

    ?

    ??? }


    ??? void onCreate (){

    ??????? Animation anim = new TranslateAnimation (10, 20, 0, 0);

    ??????? anim.setDuration (1000); // 1s

    ??????? anim.setInterpolator (new AcceleratInterpolator(3.0f));

    ??????? startAniamtion (anim);

    ??? }

    }

    ?

    原文:http://www.linuxgraphics.cn/animation/android_tween_animation.html

    轉載于:https://my.oschina.net/kevin008/blog/2195

    總結

    以上是生活随笔為你收集整理的分析android动画模块[转]的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。