二話不說(shuō),上圖先淤毛!
RecyclerView已經(jīng)出來(lái)許久了今缚,估計(jì)現(xiàn)在沒(méi)多少人使用ListView或者GridView了吧?
這篇文章講解如何計(jì)算寬高相同或不同Item的RecyclerView滑動(dòng)距離低淡,所謂的滑動(dòng)距離意思如下圖姓言。
大概思路就是先得出正在移出屏幕Item的
position,再得出該Item的寬或高蔗蹋,再得出該Item還有多少部分未移出屏幕何荚,拿
position乘寬或者高減去未移出屏幕的距離,就可以算出滑動(dòng)的距離了(?????)
先看下定義的變量和常量
//豎著
private static final int MANAGER_LINEAR_VERTICAL = 0;
//橫著一行
private static final int MANAGER_LINEAR_HORIZONTAL = 1;
//Grid 豎著
private static final int MANAGER_LINEAR_GRIDVIEW_VERTICAL = 2;
//Grid 橫著
private static final int MANAGER_LINEAR_GRIDVIEW_HORIZONTAL = 3;
//豎著不同
private static final int MANAGER_LINEAR_VERTICAL_ = 4;
//橫著不同
private static final int MANAGER_LINEAR_HORIZONTAL_ = 5;
//形態(tài)變量
private int intType = 0;
//item的寬/高
private int itemW;
private int itemH;
private int iResult;
//存放item寬或高
private Map<Integer, Integer> mMapList = new HashMap<>();
private int iposition;
Item布局
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<ImageView
android:id="@+id/iv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@mipmap/ic_tk"/>
<TextView
android:id="@+id/tv_position"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@+id/iv"
android:layout_alignTop="@+id/iv"
android:background="@color/colorPrimary"
android:textColor="#e5e5e6"
/>
</RelativeLayout>
一猪杭、計(jì)算寬高相同Item
//該方法用于監(jiān)聽(tīng)mRecyclerView的滑動(dòng)事件
mRecyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
super.onScrolled(recyclerView, dx, dy);
}
});
在上面監(jiān)聽(tīng)中調(diào)用下面計(jì)算方法餐塘,可計(jì)算出VERTICAL豎著布局的滑動(dòng)距離
//找到即將移出屏幕Item的position,position是移出屏幕item的數(shù)量
int position = linearLayoutManager.findFirstVisibleItemPosition();
//根據(jù)position找到這個(gè)Item
View firstVisiableChildView = linearLayoutManager.findViewByPosition(position);
//獲取Item的高
int itemHeight = firstVisiableChildView.getHeight();
//算出該Item還未移出屏幕的高度
int itemTop = firstVisiableChildView.getTop();
//position移出屏幕的數(shù)量*高度得出移動(dòng)的距離
int iposition = position * itemHeight;
//減去該Item還未移出屏幕的部分可得出滑動(dòng)的距離
iResult = iposition - itemTop;
若是HORIZONTAL橫著的RecyclerView則需要稍加改動(dòng)調(diào)用下面方法就能計(jì)算出滑動(dòng)距離因?yàn)槭菣M著的所以要拿到item的寬,用getRight()方法算出未移出屏幕的距離皂吮,但橫著的RecyclerView取到的第一個(gè)Item Position為零戒傻,所以隨后算總距離的時(shí)候要加上一個(gè)Item的寬度
//找到即將移出屏幕Item的position,position是移出屏幕item的數(shù)量
int position = linearLayoutManager.findFirstVisibleItemPosition();
//根據(jù)position找到這個(gè)Item
View firstVisiableChildView = linearLayoutManager.findViewByPosition(position);
//獲取Item的寬
int itemWidth = firstVisiableChildView.getWidth();
//算出該Item還未移出屏幕的高度
int itemRight = firstVisiableChildView.getRight();
//position移出屏幕的數(shù)量*高度得出移動(dòng)的距離
int iposition = position * itemWidth;
//因?yàn)闄M著的RecyclerV第一個(gè)取到的Item position為零所以計(jì)算時(shí)需要加一個(gè)寬
iResult = iposition - itemRight + itemWidth;
二、計(jì)算Grid排列相同Item
豎著的Grid蜂筹,注釋很認(rèn)真的寫(xiě)了(⊙o⊙)需纳,大部分還是一樣的
//得出spanCount幾列或幾排
int itemSpanCount = gridLayoutManager.getSpanCount();
//得出的position是一排或一列總和
int position = gridLayoutManager.findFirstVisibleItemPosition();
//需要算出才是即將移出屏幕Item的position
int itemPosition = position / itemSpanCount ;
//因?yàn)槭窍嗤腎tem所以取那個(gè)都一樣
View firstVisiableChildView = gridLayoutManager.findViewByPosition(position);
int itemHeight = firstVisiableChildView.getHeight();
int itemTop = firstVisiableChildView.getTop();
int iposition = itemPosition * itemHeight;
iResult = iposition - itemTop;
橫著的Grid大家可以下Demo看一下,也是有注釋的
三狂票、計(jì)算不同Item
思路:用Map按Position記錄了每個(gè)Item的寬或高候齿,通過(guò)
findFirstVisibleItemPosition()方法動(dòng)態(tài)計(jì)算滑動(dòng)距離
public int unlikeVertical() {
int itemWH = 0;
int itemTR = 0;
int distance = 0;
int position = linearLayoutManager.findFirstVisibleItemPosition();
View firstVisiableChildView = linearLayoutManager.findViewByPosition(position);
//判斷是橫著還是豎著,得出寬或高
if (intType == MANAGER_LINEAR_VERTICAL_) {
itemWH = firstVisiableChildView.getHeight();
} else if (intType == MANAGER_LINEAR_HORIZONTAL_) {
itemWH = firstVisiableChildView.getWidth();
}
//一層判斷mMapList是否為空闺属,若不為空則根據(jù)鍵判斷保證不會(huì)重復(fù)存入
if (mMapList.size() == 0) {
mMapList.put(position, itemWH);
} else {
if (!mMapList.containsKey(position)) {
mMapList.put(position, itemWH);
Log.d("poi", mMapList + "");
}
}
//判斷是橫著還是豎著慌盯,得出未滑出屏幕的距離
if (intType == MANAGER_LINEAR_VERTICAL_) {
itemTR = firstVisiableChildView.getTop();
} else if (intType == MANAGER_LINEAR_HORIZONTAL_) {
itemTR = firstVisiableChildView.getRight();
}
//position為動(dòng)態(tài)獲取,目前屏幕Item位置
for (int i = 0; i < position; i++) {
//iposition移出屏幕的距離
iposition = iposition + mMapList.get(i);
}
//根據(jù)類(lèi)型拿iposition減未移出Item部分距離掂器,最后得出滑動(dòng)距離
if (intType == MANAGER_LINEAR_VERTICAL_) {
distance = iposition - itemTR;
} else if (intType == MANAGER_LINEAR_HORIZONTAL_) {
distance = iposition - itemTR + itemWH;
}
//item寬高
itemW = firstVisiableChildView.getWidth();
itemH = firstVisiableChildView.getHeight();
//歸零
iposition = 0;
return distance;
}
Demo地址:github.com/NathansLiu/…
My JianShu:www.reibang.com/u/ae7a687f5…
My JueJin:https://juejin.im/user/59a0ca42f265da2491510f10
寫(xiě)完啦亚皂!