Android轉場動畫深度解析(2)

緊接着上一篇介紹了Scene和Transition的基本用法後,這篇開始介紹如何運用這些到轉場動畫中。從A頁面到B頁面,再從B頁面返回到A頁面,這就是一個完整的轉場過程。而轉場動畫就是負責來優雅地協調處理好這個過程的。android

Content Transition

Content Transition就是最多見的轉場動畫了。爲了方便你們理解,咱們先來上個圖。bash

部分代碼:

源Activity:

Slide slide=new Slide();
slide.setDuration(3000);
slide.setSlideEdge(Gravity.BOTTOM);
getWindow().setExitTransition(slide);

Explode explode = new Explode();
explode.setDuration(3000);
explode.setMode(Visibility.MODE_IN);
getWindow().setReenterTransition(explode);
複製代碼

目標Activity:

Slide slideEnter=new Slide();
slideEnter.setDuration(1500);
slideEnter.setSlideEdge(Gravity.RIGHT);
getWindow().setEnterTransition(slideEnter);

Slide slide=new Slide();
slide.setDuration(1500);
slide.setSlideEdge(Gravity.RIGHT);
getWindow().setReturnTransition(slide);
複製代碼

而後在A頁面調用方法跳到B頁面:ide

Intent intent = new Intent(this, BActivity.class);
ActivityOptionsCompat activityOptionsCompat = ActivityOptionsCompat.makeSceneTransitionAnimation(this);
startActivity(intent, activityOptionsCompat.toBundle());
複製代碼

能夠看到一共能夠設置四個Transition:佈局

  • (1)setExitTransition() - 當A 跳轉到 B時,A中的View退出場景的效果(默認Null)post

  • (2)setEnterTransition() - 當A 跳轉到 B時,B中的View進入場景的效果(默認Fade)動畫

  • (3)setReturnTransition() - 當B 返回 A時,B中的View退出場景的效果(默認同EnterTransition)ui

  • (4)setReenterTransition() - 當B 返回 A時,A中的View進入場景的效果(默認同ExitTransition)this

以上這個過程一樣能夠看作是Transition做用在Scene上的一系列效果,只不過這裏的Scene從上一篇中的單一佈局換成了Window。不過細心的同窗可能發現了,明明我爲四個過程都設置動畫效果,可爲何ExitTransition沒有生效呢?接下來咱們爲每一個Transition加入監聽,看看動畫的執行流程。下面是其中一個的代碼,其餘三個都同樣:spa

Explode explode = new Explode();
explode.setDuration(3000);
explode.setMode(Visibility.MODE_IN);
  explode.addListener(new Transition.TransitionListener(){
            @Override
            public void onTransitionStart(Transition transition) {
               
                Log.d("Transitions--","ReenterTransitionStart");
            }

            @Override
            public void onTransitionEnd(Transition transition) {
               
                Log.d("Transitions--","ReenterTransitionEnd");
            }

            @Override
            public void onTransitionCancel(Transition transition) {
                
            }

            @Override
            public void onTransitionPause(Transition transition) {

            }

            @Override
            public void onTransitionResume(Transition transition) {

            }
        });
   getWindow().setReenterTransition(explode);
複製代碼

再次執行程序,日誌信息以下: 3d

原來A頁面的退出動畫和B頁面的進入動畫、B頁面的返回動畫和A頁面的重現動畫是並行執行的。也就是說A頁面的ExitTransition不是沒有執行,而是在它執行的時候,B頁面已經覆蓋上來,而且EnterTransition已經同時在執行了,這時A頁面已經不可見了。這也是Android默認的轉場動畫執行流程。 那問題來了,若是想要串行執行該怎麼辦呢? 有兩種方法: 在設置Transition的時候同時設置不容許Transition重疊,也就是並行執行:

getWindow().setAllowEnterTransitionOverlap(false);
getWindow().setWindowAllowReturnTransitionOverlap(false);
複製代碼

或者在主題文件全局設置這個屬性,這樣無疑更好,即減小了代碼又保證了應用視覺效果的統一:

<item name="android:windowAllowEnterTransitionOverlap">false</item>
<item name="android:windowAllowReturnTransitionOverlap">false</item>
複製代碼

修改後效果以下:

日誌也顯示如今是串行執行了:

生命週期分析

保持上面的打印信息不變,咱們增長兩個Activity的生命週期日誌信息,串行結果以下:

並行以下:

能夠獲得以下信息:

  • 在A頁面的onPause執行前,ExitTransition就已經開始執行了
  • Transition不會阻塞BActivity的生命週期,儘管是串行執行的,即便ExitTransition沒結束,BActivity已經執行完OnResume了。
  • ReturnExitTransition須要等到AActivity OnStart執行完纔開始執行,並且ReturnExitTransition會阻塞AActivity的生命週期,AActivity的OnResume會等到ReturnExitTransition執行完再執行。關於這點能夠簡要說明下:直接調用Finish不會有動畫直接結束掉,須要執行onBackPressed()纔會有ReturnExitTransition。看源碼就很明顯了:
public void onBackPressed() {
        if (mActionBar != null && mActionBar.collapseActionView()) {
            return;
        }

        if (!mFragments.getFragmentManager().popBackStackImmediate()) {
            finishAfterTransition();
        }
    }

複製代碼

總結

最後簡單分析下轉場動畫的大體流程(以slide爲例),看過上一篇文章的同窗應該很好理解:

1.從DecoerView開始,依次遍歷得到當前Window上的視圖樹裏的全部View

2.執行captureStartValues(TransitionValues transitionValues),捕獲View開始狀態的一些屬性(visibility,Parent,LocationOnScree)

3.設置全部的VIew爲INVISIBLE。

4.執行captureEndValues(TransitionValues transitionValues),捕獲View結束狀態的一些屬性(visibility,Parent,LocationOnScree)

5.比較屬性的不一樣,建立屬性動畫。下一個過程就是返回屬性動畫並執行了。
複製代碼

這是ExitTransiton的流程,其餘三個也差很少。下一篇將會講帶共享元素的轉場動畫,也是material design中頗有特點的動畫了。

相關文章
相關標籤/搜索