新年好,首先給你們發個紅包。javascript
[意念紅包]請閉上眼睛經過念力領取。php
本文同步自wing的地方酒館html
這都2017年了,是時候來一波基礎特效教程了!java
若是我不偷懶的話,或許能夠成爲一個系列都基礎教程哦。固然若是成爲了一個系列,這個系列就像標題說的同樣,是基礎特效。因此內容會比較簡單,若是你是老司機的話,能夠直接飄過了(順便帶我上車!)。android
本次項目地址:github.com/githubwing/…git
此次依然拿餓了麼開刀。來庖丁一個搜索欄過分效果,以下圖:github
額,圖片仍是比較大的,爲了避免浪費排版空間,此次就不上餓了麼原圖了,直接上效果圖。效果仍是差很少的哈。微信
如你所見,這是一個過分效果。 用一個羣友的話來講就是絲滑過分根本看不出來是兩個Activity。ide
這是兩個Activity,看起來順化的緣由是使用了一種叫作共享元素的概念。Android 5.0自帶共享元素的實現,可是有一些缺點好比:不能改變大小, 不能兼容4.X 等等。動畫
其實本次的效果在高仿微信下滑返回PhotoView中有運用以及介紹。可是因爲篇幅沒有作詳細的介紹,如今就向你們介紹實現這種效果的思路。
首先既然叫作共享元素,那麼可想而知確定有兩個Activity擁有一項共同的元素,多是圖片、一個TextView、一個EditText等等。如效果圖,他就是共享一整個EditText。準確地說是一個組成看似EditText的元素組。
爲了實現這個效果,咱們須要在兩個Activity中都放置一樣的搜索欄元素。
<FrameLayout
android:layout_width="match_parent"
android:layout_height="150dp"
android:background="#0096FF"
android:padding="10dp">
<TextView
android:layout_marginLeft="10dp"
android:layout_marginTop="20dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="廣東省廣州市番禺區"
android:textColor="#fff"
android:textSize="16sp" />
<TextView
android:id="@+id/tv_search_bg"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:background="@drawable/ele_search_bg"
android:gravity="center"
android:padding="10dp" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center"
android:text="搜索商家、商品名稱" />
<TextView
android:gravity="center"
android:textColor="#fff"
android:text="燒烤 螺螄粉 火鍋 巴掌 麥當勞 冒菜 臭豆腐 雲吞麪 "
android:layout_gravity="bottom"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</FrameLayout>複製代碼
如今咱們兩個Activity都有這個元素了。接下來要作的只有一步:那就是startActivity。
哈哈,我真的沒有逗你,由於其實全部你看到的動畫都是在第二個Activity完成的。由效果圖能夠看到,在動畫執行的過程當中仍是能夠看到前一個Activity的,因此咱們須要對第二個Activity進行特殊的「透明處理」。
在style.xml裏面新增長一個透明的主題,而且應用給第二個Activity。
<style name="Translucent" parent="Theme.AppCompat.Light.NoActionBar">
<item name="android:windowBackground">@android:color/transparent</item>
<item name="android:windowIsTranslucent">true</item>
</style>複製代碼
接下來,只要在第二個Activity打開的時候,進行一些動畫便可。因此首先咱們要把第一個Activity中元素的座標傳給第二個Activity。
Intent intent = new Intent(EleActivity.this,EleSearchActivity.class);
int location[] = new int[2];
mSearchBGTxt.getLocationOnScreen(location);
intent.putExtra("x",location[0]);
intent.putExtra("y",location[1]);
startActivity(intent);
overridePendingTransition(0,0);複製代碼
注意這裏拿到的是在屏幕中的座標。因此在第二個Activity中,獲取第二個元素的座標也要用屏幕中的座標。
拿到以後,再根據兩個座標的差值進行平移操做,這樣位移起來就徹底不須要考慮其餘座標系了。至於爲何,留個做業(斜眼):
float originY = getIntent().getIntExtra("y", 0);
int location[] = new int[2];
mSearchBGTxt.getLocationOnScreen(location);
float translateY = originY - (float) location[1];複製代碼
若是你想要預覽位置效果,能夠直接view.setTranslateY(translateY);
接下來動畫只要交給ValueAnimator,在這裏把搜索欄的背景單獨抽成一個View,用來進行X縮放操做。因此如今要作的動畫有:
translateVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator valueAnimator) {
mSearchBGTxt.setY((Float) valueAnimator.getAnimatedValue());
mArrowImg.setY(mSearchBGTxt.getY() + (mSearchBGTxt.getHeight() - mArrowImg.getHeight()) / 2);
mHintTxt.setY(mSearchBGTxt.getY() + (mSearchBGTxt.getHeight() - mHintTxt.getHeight()) / 2);
mSearchTxt.setY(mSearchBGTxt.getY() + (mSearchBGTxt.getHeight() - mSearchTxt.getHeight()) / 2);
}
});複製代碼
等動畫執行完畢之後,只須要將View正確歸爲便可!
固然返回的時候,只須要往相反的地方作動畫~ 另外還須要特別注意的地方有,在啓動或者關閉Activity的時候,須要調用下面的代碼來關閉切換動畫來保證效果。
overridePendingTransition(0, 0);複製代碼
感受此次效果雖然簡單,可是應用場景仍是挺廣得。
本次項目地址:github.com/githubwing/…
若是你喜歡 歡迎Star,也能夠加入個人Android酒館:425983695
參考文章: 低版本實現共享元素動畫