在Material Design中有很多很炫的動畫,這些動畫在提升了與用戶交互體驗的同時,也增加了Android App的界面效果。現(xiàn)在的Android在Android M上,個人覺得在交互方面已經(jīng)不輸給任何的iphone。甚至在ios中,也有很多的效果在借鑒android?,F(xiàn)在的開發(fā)中 廣大的產(chǎn)品經(jīng)理們可以不用以iphone的效果為基準(zhǔn)了。
MD中的Activity的轉(zhuǎn)場動畫
要實現(xiàn)MD中的Activity的轉(zhuǎn)場動畫效果。我們可以使用ActivityOptions類。但是這個類只支持API21以上的版本。但是對于要兼容低版本的app中,我們需要進(jìn)行版本的判斷,版本判斷就比較麻煩,但是貼心的谷歌為我們設(shè)計了一個兼容類:ActivityOptionsCompat 位于android.support.v4包中,但是這個類在低版本上面并沒有轉(zhuǎn)場效果。只是解決了我們手動去判斷版本的問題而已。也就是說這個類可以實現(xiàn)的是在高版本上會有Activity的轉(zhuǎn)場效果。而在低版本上沒有。
別廢話,開擼
Activity轉(zhuǎn)場動畫的使用
Activity轉(zhuǎn)場動畫就是在兩個Activity進(jìn)行跳轉(zhuǎn)的時候執(zhí)行的動畫。
轉(zhuǎn)場動畫分為兩大類:共享元素轉(zhuǎn)換和普通轉(zhuǎn)換
使用轉(zhuǎn)換動畫的前提:需要設(shè)置Activity允許使用轉(zhuǎn)場動畫
由于轉(zhuǎn)場動畫是整個的界面的Window實現(xiàn)一個轉(zhuǎn)場的效果。所以我們需要在onCreate之前拿到window對象并設(shè)置Feature
- 方法一 代碼設(shè)置
//設(shè)置使用轉(zhuǎn)場動畫
getWindow().requestFeature(Window.FEATURE_CONTENT_TRANSITIONS);
- 方法二 xml
<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">@color/colorPrimary</item>
<item name="colorPrimaryDark">@color/colorPrimaryDark</item>
<item name="colorAccent">@color/colorAccent</item>
<item name="android:windowContentTransitions">true</item>
</style>
使用ActivityOptionsCompat 共享元素轉(zhuǎn)換
我們使用共享元素跳轉(zhuǎn),就是在跳轉(zhuǎn)的時候會共享一個元素,共享元素的觀念就是可以把兩個Activity當(dāng)中相同的元素關(guān)聯(lián)起來做連貫的動畫。
前提,給兩個Activity當(dāng)中的共享元素view都設(shè)置一個相同的名字——android:transitionName
- xml文件中
<ImageView
android:id="@+id/iv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:transitionName="iv_meinv3"
android:src="@drawable/meinv3" />
按返回鍵的時候我們可以看到,過渡動畫還是可以返回共享元素的轉(zhuǎn)場動畫,在源碼中可以看到系統(tǒng)會判斷是否支持了轉(zhuǎn)場動畫,來執(zhí)行不同策略的回退
finishAfterTransition()
- Activity文件中
@RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN)
public void jumpPage(View view) {
ActivityOptionsCompat optionsCompat = ActivityOptionsCompat.makeSceneTransitionAnimation(
this,
iv,
"iv_meinv3"
);
Intent intent = new Intent(this, Scene2Activity.class);
startActivity(intent, optionsCompat.toBundle());
}
處理多個共享元素的情況
- xml文件中要對每個控件的android:transitionName都指定一個名字
- 第一個activity的布局文件xml
<ImageView
android:id="@+id/iv"
android:layout_width="200dp"
android:layout_height="200dp"
android:scaleType="fitXY"
android:src="@drawable/meinv3"
android:transitionName="iv"
/>
<Button
android:id="@+id/bt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="jumpPage"
android:transitionName="bt"
android:text="跳轉(zhuǎn)" />
- 第二個activity的布局文件的xml
<ImageView
android:id="@+id/iv2"
android:layout_width="300dp"
android:layout_height="300dp"
android:scaleType="fitXY"
android:src="@drawable/meinv3"
android:transitionName="iv"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent" />
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="我就是個按鈕"
android:transitionName="bt"
app:layout_constraintTop_toBottomOf="@+id/iv2"
/>
- activity中使用Pair
ActivityOptionsCompat optionsCompat = ActivityOptionsCompat.makeSceneTransitionAnimation(this,
Pair.create((View) iv, "iv"), Pair.create((View) bt, "bt"));
Intent intent = new Intent(this, Scene2Activity.class);
startActivity(intent, optionsCompat.toBundle());
使用ActivityOptionsCompat 普通元素轉(zhuǎn)換
普通的轉(zhuǎn)換效果可以使用系統(tǒng)自帶
三種系統(tǒng)帶的:滑動效果(Slide)、展開效果Explode、漸變顯示隱藏效果Fade
Slide slide = new Slide();
slide.setDuration(300);
getWindow().setExitTransition(slide);//出去的動畫
getWindow().setEnterTransition(slide);//進(jìn)來的動畫
Explode explode = new Explode();
explode.setDuration(1000);
getWindow().setExitTransition(explode);//出去的動畫
getWindow().setEnterTransition(explode);//進(jìn)來的動畫
Fade fade = new Fade();
fade.setDuration(1000);
getWindow().setExitTransition(fade);//出去的動畫
getWindow().setEnterTransition(fade);//進(jìn)來的動畫
//如果有共享元素,可以設(shè)置共享元素,那么它就會按照共享元素動畫執(zhí)行,其他的子view就會按照Fade動畫執(zhí)行。
ActivityOptionsCompat optionsCompat = ActivityOptionsCompat.makeSceneTransitionAnimation(MainActivity.this);
Intent intent = new Intent(this, SecondActivity.class);
startActivity(intent, optionsCompat.toBundle());