recyclerView新增自定義分割線
阿新 • • 發佈:2019-01-02
recyclerview可以通過addItemDecoration()方法實現新增自定義分割線的功能。比如需要實現如下圖功能
首先自己定義類繼承自RecyclerView.ItemDecoration
其次在drawable資料夾下新建xml檔案定義間隔線寬度與顏色public class MyDividerDecoration extends RecyclerView.ItemDecoration { private static final int[] ATTRS = new int[]{ android.R.attr.listDivider }; /** * 用於繪製間隔樣式 */ private Drawable mDivider; public MyDividerDecoration(Context context) { // 獲取預設主題的屬性 final TypedArray a = context.obtainStyledAttributes(ATTRS); mDivider = a.getDrawable(0); a.recycle(); } @Override public void onDraw(Canvas c, RecyclerView parent, RecyclerView.State state) { // 繪製間隔,每一個item,繪製右邊和下方間隔樣式 int childCount = parent.getChildCount(); int spanCount = ((GridLayoutManager)parent.getLayoutManager()).getSpanCount(); int orientation = ((GridLayoutManager)parent.getLayoutManager()).getOrientation(); boolean isDrawHorizontalDivider = true; boolean isDrawVerticalDivider = true; int extra = childCount % spanCount; extra = extra == 0 ? spanCount : extra; for(int i = 0; i < childCount; i++) { isDrawVerticalDivider = true; isDrawHorizontalDivider = true; // 如果是豎直方向,最右邊一列不繪製豎直方向的間隔 if(orientation == OrientationHelper.VERTICAL && (i + 1) % spanCount == 0) { isDrawVerticalDivider = false; } // 如果是豎直方向,最後一行不繪製水平方向間隔 if(orientation == OrientationHelper.VERTICAL && i >= childCount - extra) { isDrawHorizontalDivider = false; } // 如果是水平方向,最下面一行不繪製水平方向的間隔 if(orientation == OrientationHelper.HORIZONTAL && (i + 1) % spanCount == 0) { isDrawHorizontalDivider = false; } // 如果是水平方向,最後一列不繪製豎直方向間隔 if(orientation == OrientationHelper.HORIZONTAL && i >= childCount - extra) { isDrawVerticalDivider = false; } if(isDrawHorizontalDivider) { drawHorizontalDivider(c, parent, i); } if(isDrawVerticalDivider) { drawVerticalDivider(c, parent, i); } } } @Override public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) { int spanCount = ((GridLayoutManager) parent.getLayoutManager()).getSpanCount(); int orientation = ((GridLayoutManager)parent.getLayoutManager()).getOrientation(); int position = parent.getChildLayoutPosition(view); if(orientation == OrientationHelper.VERTICAL && (position + 1) % spanCount == 0) { outRect.set(0, 0, 0, mDivider.getIntrinsicHeight()); return; } if(orientation == OrientationHelper.HORIZONTAL && (position + 1) % spanCount == 0) { outRect.set(0, 0, mDivider.getIntrinsicWidth(), 0); return; } outRect.set(0, 0, mDivider.getIntrinsicWidth(), mDivider.getIntrinsicHeight()); } /** * 繪製豎直間隔線 * * @param canvas * @param parent * 父佈局,RecyclerView * @param position * irem在父佈局中所在的位置 */ private void drawVerticalDivider(Canvas canvas, RecyclerView parent, int position) { final View child = parent.getChildAt(position); final RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child .getLayoutParams(); final int top = child.getTop() - params.topMargin; final int bottom = child.getBottom() + params.bottomMargin + mDivider.getIntrinsicHeight(); final int left = child.getRight() + params.rightMargin; final int right = left + mDivider.getIntrinsicWidth(); mDivider.setBounds(left, top, right, bottom); mDivider.draw(canvas); } /** * 繪製水平間隔線 * * @param canvas * @param parent * 父佈局,RecyclerView * @param position * item在父佈局中所在的位置 */ private void drawHorizontalDivider(Canvas canvas, RecyclerView parent, int position) { final View child = parent.getChildAt(position); final RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child .getLayoutParams(); final int top = child.getBottom() + params.bottomMargin; final int bottom = top + mDivider.getIntrinsicHeight(); final int left = child.getLeft() - params.leftMargin; final int right = child.getRight() + params.rightMargin + mDivider.getIntrinsicWidth(); mDivider.setBounds(left, top, right, bottom); mDivider.draw(canvas); } }
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="@color/bg_gray"/>
<size android:height="2dp" android:width="2dp"/>
</shape>
然後在styles.xml中定義的應用主題裡替換掉listdivider屬性。接下來就是呼叫了<style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar"> <!-- Customize your theme here. --> <item name="colorPrimary">@color/colorPrimary</item> <item name="colorPrimaryDark">@color/colorPrimaryDark</item> <item name="colorAccent">@color/colorAccent</item> <item name="android:listDivider">@drawable/my_divider</item> </style>
recyclerview.addItemDecoration(new MyDividerDecoration(this));
到這裡新增分割線的功能就實現了