Android仿QQ左滑刪除置頂ListView操作
最近閑來無事,于是研究了一下qq的左滑刪除效果,嘗試著實現(xiàn)了一下,先上效果圖:
大致思路原理:
- 通過設(shè)置margin實現(xiàn)菜單的顯示與隱藏
- 監(jiān)聽onTouchEvent,處理滑動事件
上代碼
import android.content.Context; import android.util.AttributeSet; import android.util.DisplayMetrics; import android.view.MotionEvent; import android.view.ViewGroup; import android.view.WindowManager; import android.widget.LinearLayout; import android.widget.ListView; /** * Created by MooreLi on 2016/8/8. */ public class SlideListView extends ListView { private String TAG = getClass().getSimpleName(); private int mScreenWidth; private int mDownX; private int mDownY; private int mMenuWidth; private boolean isMenuShow; private boolean isMoving; private int mOperatePosition = -1; private ViewGroup mPointChild; private LinearLayout.LayoutParams mLayoutParams; public SlideListView(Context context) { super(context); getScreenWidth(context); } public SlideListView(Context context, AttributeSet attrs) { super(context, attrs); getScreenWidth(context); } public SlideListView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); getScreenWidth(context); } private void getScreenWidth(Context context) { WindowManager manager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE); DisplayMetrics dm = new DisplayMetrics(); manager.getDefaultDisplay().getMetrics(dm); mScreenWidth = dm.widthPixels; } @Override public boolean onTouchEvent(MotionEvent ev) { switch (ev.getAction()) { case MotionEvent.ACTION_DOWN: performActionDown(ev); break; case MotionEvent.ACTION_MOVE: performActionMove(ev); break; case MotionEvent.ACTION_UP: performActionUp(); break; } return super.onTouchEvent(ev); } private void performActionDown(MotionEvent ev) { mDownX = (int) ev.getX(); mDownY = (int) ev.getY(); //如果點擊的不是同一個item,則關(guān)掉正在顯示的菜單 int position = pointToPosition(mDownX, mDownY); if (isMenuShow && position != mOperatePosition) { turnToNormal(); } mOperatePosition = position; mPointChild = (ViewGroup) getChildAt(position - getFirstVisiblePosition()); if (mPointChild != null) { mMenuWidth = mPointChild.getChildAt(1).getLayoutParams().width; mLayoutParams = (LinearLayout.LayoutParams) mPointChild.getChildAt(0).getLayoutParams(); mLayoutParams.width = mScreenWidth; setChildLayoutParams(); } } private boolean performActionMove(MotionEvent ev) { int nowX = (int) ev.getX(); int nowY = (int) ev.getY(); // if (isMoving) { // if (Math.abs(nowY - mDownY) > 0) { // Log.e(TAG, "kkkkkkk"); // onInterceptTouchEvent(ev); // } // } if (Math.abs(nowX - mDownX) > 0) { //左滑 顯示菜單 if (nowX < mDownX) { if (isMenuShow) { mLayoutParams.leftMargin = -mMenuWidth; } else { //計算顯示的寬度 int scroll = (nowX - mDownX); if (-scroll >= mMenuWidth) { scroll = -mMenuWidth; } mLayoutParams.leftMargin = scroll; } } //右滑 如果菜單顯示狀態(tài),則關(guān)閉菜單 if (isMenuShow && nowX > mDownX) { int scroll = nowX - mDownX; if (scroll >= mMenuWidth) { scroll = mMenuWidth; } mLayoutParams.leftMargin = scroll - mMenuWidth; } setChildLayoutParams(); isMoving = true; return true; } return super.onTouchEvent(ev); } private void performActionUp() { //超過一半時,顯示菜單,否則隱藏 if (-mLayoutParams.leftMargin >= mMenuWidth / 2) { mLayoutParams.leftMargin = -mMenuWidth; setChildLayoutParams(); isMenuShow = true; } else { turnToNormal(); } isMoving = false; } private void setChildLayoutParams(){ if(mPointChild != null){ mPointChild.getChildAt(0).setLayoutParams(mLayoutParams); } } /** * 正常顯示 */ public void turnToNormal() { mLayoutParams.leftMargin = 0; mOperatePosition = -1; setChildLayoutParams(); isMenuShow = false; } }
item的布局要注意,因為在自定義view中寫死的是獲取第一個子布局為顯示內(nèi)容,所以需要將顯示的樣式寫在一個容器中,將菜單寫在另一個容器中,兩個平行的關(guān)系。
xml文件定義如下:
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="#FFFFFF" android:orientation="horizontal"> <LinearLayout android:layout_width="match_parent" android:layout_height="60dp" android:orientation="horizontal"> <TextView android:id="@+id/main_tv_title" android:layout_width="wrap_content" android:layout_height="match_parent" android:layout_marginLeft="10dp" android:gravity="center_vertical" android:textSize="18sp" /> </LinearLayout> <LinearLayout android:layout_width="180dp" android:layout_height="60dp" android:orientation="horizontal"> <TextView android:id="@+id/main_tv_delete" android:layout_width="0dp" android:layout_height="match_parent" android:layout_weight="1" android:background="#FF0000" android:gravity="center" android:text="刪除" android:textColor="#FFFFFF" /> <TextView android:id="@+id/main_tv_top" android:layout_width="0dp" android:layout_height="match_parent" android:layout_weight="1" android:background="#DFCDBF" android:gravity="center" android:text="置頂" android:textColor="#FFFFFF" /> </LinearLayout> </LinearLayout>
最后就是刪除操作與置頂操作,這個就比較簡單,給按鈕添加點擊事件即可。我是在adapter中定義實現(xiàn),記得操作后要將菜單關(guān)掉!
上部分代碼:
holder.tvTitle.setText(mInfos.get(position)); holder.tvDelete.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { mInfos.remove(position); notifyDataSetChanged(); mListView.turnToNormal(); } }); holder.tvTop.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { String temp = mInfos.get(position); mInfos.remove(position); mInfos.add(0, temp); notifyDataSetChanged(); mListView.turnToNormal(); } });
最后還有一個遺留問題,ListView左右滑動的時候上下也會滑動,這個有待探索與改進,也希望大家提提意見,幫我改進!
以上就是本文的全部內(nèi)容,希望對大家的學習有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
Android實現(xiàn)可輸入數(shù)據(jù)的彈出框
這篇文章主要為大家詳細介紹了Android實現(xiàn)可輸入數(shù)據(jù)的彈出框,文章提供了兩種方式,示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下2016-01-01Android編程實現(xiàn)自定義ImageView圓圖功能的方法
這篇文章主要介紹了Android編程實現(xiàn)自定義ImageView圓圖功能的方法,結(jié)合實例形式分析了Android自定義ImageView及實現(xiàn)圓圖效果的具體步驟與相關(guān)操作技巧,需要的朋友可以參考下2017-08-08Android 用HttpURLConnection訪問網(wǎng)絡的方法
下面小編就為大家分享一篇Android 用HttpURLConnection訪問網(wǎng)絡的方法,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2018-01-01在Android Studio中設(shè)置Button透明度的方法詳解
本文將介紹在Android Studio中如何設(shè)置Button的透明度,首先,我們將展示實現(xiàn)該功能的整個流程,并使用表格列出每個步驟,然后,我們將詳細說明每個步驟需要做什么,并提供相應的代碼和注釋,需要的朋友可以參考下2023-09-09Android RadioGroup 設(shè)置某一個選中或者不可選中的方法
下面小編就為大家?guī)硪黄狝ndroid RadioGroup 設(shè)置某一個選中或者不可選中的方法。小編覺得挺不錯的,現(xiàn)在就分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2017-04-04Android 游戲引擎libgdx 資源加載進度百分比顯示案例分析
因為案例比較簡單,所以簡單用AndroidApplication -> Game -> Stage 搭建框架感興趣的朋友可以參考下2013-01-01Android應用開發(fā)中Fragment與Activity間通信示例講解
這篇文章主要介紹了Android應用開發(fā)中Fragment與Activity間通信實例講解,需要的朋友可以參考下2016-02-02