1.前言
我们的产品经常会出现这样的界面:
需求是:点击不同的tab后,需要更新RecyclerView上的内容。再次点击之前的tab要停留在之前的位置。
说明:每个item样式是一样的,但是由于标题和内容导致每个item的高度不一样。
2.实现方式
1.使用ViewPager嵌套n个RecyclerView
2.使用单个RecyclerView实现
就实现的复杂度而言,肯定是1会比较容易。但是就性能而言没必要创建多个RecyclerView。
下面说下使用单个RecyclerView实现这个需求的实现逻辑。
3.需要解决的问题
1. 记录RecyclerView在不同tab下的滑动位置
2. 切换到之前的tab后,需要准确定位到之前的位置
3.记录每个界面的数据,切换tab后进行数据替换
实现难点在于精确定位到RecyclerView之前的位置,因为item的高度不确定的。
不可行方案:
public class OffsetLinearLayoutManager extends LinearLayoutManager { public OffsetLinearLayoutManager(Context context) { super(context);
} private Map<Integer, Integer> heightMap = new HashMap<>(); @Override
public void onLayoutCompleted(RecyclerView.State state) { super.onLayoutCompleted(state); int count = getChildCount(); for (int i = 0; i < count ; i++) {
View view = getChildAt(i);
heightMap.put(i, view.getHeight());
}
} @Override
public int computeVerticalScrollOffset(RecyclerView.State state) { if (getChildCount() == 0) { return 0;
} try { int firstVisiablePosition = findFirstVisibleItemPosition();
View firstVisiableView = findViewByPosition(firstVisiablePosition); int offsetY = -(int) (firstVisiableView.getY()); for (int i = 0; i < firstVisiablePosition; i++) {
offsetY += heightMap.get(i) == null ? 0 : heightMap.get(i);
} return offsetY;
} catch (Exception e) { return 0;
}
}
}
待写