Android實(shí)現(xiàn)簡(jiǎn)單的下拉阻尼效應(yīng)示例代碼
OS的下拉上拉都會(huì)出現(xiàn)一個(gè)很玄的動(dòng)態(tài)效果。在Android中,雖然可以實(shí)現(xiàn)類似的效果,但有點(diǎn)不同的是,如果調(diào)用overScrollBy來(lái)實(shí)現(xiàn)類似的阻尼效應(yīng)的話,最頂部會(huì)出現(xiàn)一片亮的區(qū)域,讓人感覺(jué)不是很爽。所以決定不采用該方法來(lái)實(shí)現(xiàn)而是改用自定義的方式來(lái)實(shí)現(xiàn)。
下面是自定義控件的代碼部分:
public class MyView extends ScrollView { //記錄下最開(kāi)始點(diǎn)擊的位置 int initY; //移動(dòng)的位置 int deltaY; int touchY; //記錄第一個(gè)item的位置的矩形 Rect topRect; //用來(lái)存放第一個(gè)可見(jiàn)的item View inner; //記錄下ImageView最原始的頂部位置和底部位置 int initTop,initButtom; int left = 0,top = 0,right = 0,bottom = 0; ImageView imageView; State state; boolean recordFlag; enum State { UP,NORMAL,DOWN } boolean isMoving; boolean shutScroll; private int current_Bottom; private int current_Top; public MyView(Context context, AttributeSet attrs) { super(context, attrs); state = State.NORMAL; topRect=new Rect(); recordFlag=false; } public void setImageView(ImageView imageView) { this.imageView=imageView; } //當(dāng)布局加載完成之后調(diào)用該方法 @Override protected void onFinishInflate() { super.onFinishInflate(); //返回加載完成后所看到的第一個(gè)item,這里就是看到的第一個(gè)item,通過(guò)對(duì)該對(duì)象的移動(dòng)來(lái)實(shí)現(xiàn)整體的移動(dòng) inner=getChildAt(0); Log.i("inner", inner.toString()); } //onTouchEvent的返回值 返回true的話表示該事件已經(jīng)被處理了,返回false表示改時(shí)間還未被處理 @Override public boolean onTouchEvent(MotionEvent ev) { if(inner!=null) { commOnTouchEvent(ev); } if(shutScroll) { return true; }else { return super.onTouchEvent(ev); } } private void commOnTouchEvent(MotionEvent ev) { switch(ev.getAction()) { case MotionEvent.ACTION_DOWN: { if(recordFlag==false) { left=inner.getLeft(); top=inner.getTop(); right=inner.getRight(); bottom=inner.getBottom(); recordFlag=true; } //開(kāi)始的時(shí)候接觸點(diǎn)的坐標(biāo)值 initY=(int) ev.getY(); //記錄下ImageView的原始高度 initTop=imageView.getTop(); //記錄下ImageView的原始的底部的像素坐標(biāo) initButtom=imageView.getBottom(); break; } case MotionEvent.ACTION_MOVE: { //滑動(dòng)的距離 deltaY=(int) (ev.getY()-initY); if(deltaY<0) { //向上滑動(dòng) state=State.UP; isMoving=false; shutScroll=false; } else if(deltaY>=0) { //在這里做一下判斷,當(dāng)getScrollY為0時(shí),繼續(xù)下拉就會(huì)進(jìn)入down狀態(tài)。 if(getScrollY()==0) { //向下滑動(dòng) state=State.DOWN; isMoving=true; shutScroll=true; } } if(isMoving) { if (topRect.isEmpty()) { // 保存正常的布局位置 topRect.set(left, top,right,bottom); } float inner_move_H = deltaY / 5; inner.layout(topRect.left, (int) (topRect.top + inner_move_H), topRect.right, (int) (topRect.bottom + inner_move_H)); float image_move_H = deltaY / 10; current_Top = (int) (initTop + image_move_H); current_Bottom = (int) (initButtom + image_move_H); imageView.layout(imageView.getLeft(), current_Top, imageView.getRight(), current_Bottom); } break; } case MotionEvent.ACTION_UP: { if(needToScroll()) { animation(); } if(getScrollY()==0) { /*這里為什么要這么寫(xiě)呢?這里有很重要的一個(gè)知識(shí)點(diǎn): * getScrollY()返回的是手機(jī)屏幕左上角和調(diào)用該方法的view的左上角之間的Y坐標(biāo)只差。 * 在這里,自定義空間的布局方式看看布局文件就會(huì)發(fā)現(xiàn),當(dāng)View滑動(dòng)的時(shí)候,View的狀態(tài)在up,normal; * down之間切換。在View下來(lái)的過(guò)程中,normal和down有一個(gè)臨界值,這個(gè)臨界值就是該view的 * 左上角是不是和屏幕的左上角相等。相等的話就說(shuō)明再向下拉的話就down狀態(tài)了。*/ state=State.NORMAL; } break; } } } private void animation() { //背景圖片平移的動(dòng)畫(huà) TranslateAnimation image_Anim = new TranslateAnimation(0, 0, Math.abs(initTop - current_Top), 0); image_Anim.setDuration(200); imageView.startAnimation(image_Anim); imageView.layout(imageView.getLeft(), (int) initTop, imageView.getRight(), (int) initButtom); // 開(kāi)啟移動(dòng)動(dòng)畫(huà) TranslateAnimation inner_Anim = new TranslateAnimation(0, 0, inner.getTop(), topRect.top); inner_Anim.setDuration(200); inner.startAnimation(inner_Anim); inner.layout(topRect.left, topRect.top, topRect.right, topRect.bottom); //state=State.NORMAL; topRect.setEmpty(); } private boolean needToScroll() { if(state==State.DOWN) { return true; } return false; } }
以上這篇Android實(shí)現(xiàn)簡(jiǎn)單的下拉阻尼效應(yīng)示例代碼就是小編分享給大家的全部?jī)?nèi)容了,希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。
- Android下拉刷新完全解析,教你如何一分鐘實(shí)現(xiàn)下拉刷新功能(附源碼)
- Android實(shí)現(xiàn)聯(lián)動(dòng)下拉框 下拉列表spinner的實(shí)例代碼
- Android中Spinner(下拉框)控件的使用詳解
- Android下拉刷新ListView——RTPullListView(demo)
- Android PullToRefreshLayout下拉刷新控件的終結(jié)者
- Android中使用RecyclerView實(shí)現(xiàn)下拉刷新和上拉加載
- Android下拉刷新上拉加載控件(適用于所有View)
- Android官方下拉刷新控件SwipeRefreshLayout使用詳解
- Android屬性動(dòng)畫(huà)實(shí)現(xiàn)布局的下拉展開(kāi)效果
- Android下拉阻尼效果實(shí)現(xiàn)原理及簡(jiǎn)單實(shí)例
相關(guān)文章
android實(shí)現(xiàn)用戶體驗(yàn)超棒的微信WebView進(jìn)度條
本篇文章主要介紹了android實(shí)現(xiàn)用戶體驗(yàn)超棒的微信WebView進(jìn)度條,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2017-03-03Android 加載大圖、多圖和LruCache緩存詳細(xì)介紹
這篇文章主要介紹了Android 加載大圖、多圖和LruCache緩存詳細(xì)介紹的相關(guān)資料,需要的朋友可以參考下2016-10-10Android編程實(shí)現(xiàn)3D滑動(dòng)旋轉(zhuǎn)效果的方法
這篇文章主要介紹了Android編程實(shí)現(xiàn)3D滑動(dòng)旋轉(zhuǎn)效果的方法,主要通過(guò)繼承Animation自定義Rotate3D來(lái)實(shí)現(xiàn)3D翻頁(yè)效果,具有一定參考借鑒價(jià)值,需要的朋友可以參考下2015-11-11Android實(shí)現(xiàn)復(fù)制Assets文件到SD卡
這篇文章主要為大家詳細(xì)介紹了Android實(shí)現(xiàn)復(fù)制Assets文件到SD卡,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-12-12Android無(wú)障礙自動(dòng)化結(jié)合opencv實(shí)現(xiàn)支付寶能量自動(dòng)收集操作方法
opencv可以進(jìn)行圖像識(shí)別,兩者結(jié)合在一起即可實(shí)現(xiàn)支付寶能量自動(dòng)收集,opencv用于識(shí)別能量,無(wú)障礙服務(wù)用于模擬手勢(shì),即點(diǎn)擊能量,這篇文章主要介紹了Android無(wú)障礙自動(dòng)化結(jié)合opencv實(shí)現(xiàn)支付寶能量自動(dòng)收集,需要的朋友可以參考下2024-07-07Android自定義橫向滑動(dòng)菜單的實(shí)現(xiàn)
這篇文章主要介紹了Android自定義橫向滑動(dòng)菜單的實(shí)現(xiàn),小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2018-05-05Android自定義Adapter的ListView的思路及代碼
Android自定義Adapter的ListView的思路及代碼,需要的朋友可以參考一下2013-05-05Android Studio的安裝及第一次啟動(dòng)時(shí)的配置問(wèn)題
這篇文章主要介紹了Android Studio的安裝及第一次啟動(dòng)時(shí)的配置,需要的朋友可以參考下2019-09-09