-
Star
(170)
You must be signed in to star a gist -
Fork
(23)
You must be signed in to fork a gist
-
-
Save lapastillaroja/858caf1a82791b6c1a36 to your computer and use it in GitHub Desktop.
import android.content.Context; | |
import android.content.res.TypedArray; | |
import android.util.AttributeSet; | |
import android.support.v7.widget.RecyclerView; | |
import android.support.v7.widget.LinearLayoutManager; | |
import android.view.View; | |
import android.graphics.Rect; | |
import android.graphics.drawable.Drawable; | |
import android.graphics.Canvas; | |
public class DividerItemDecoration extends RecyclerView.ItemDecoration { | |
private Drawable mDivider; | |
public DividerItemDecoration(Context context, AttributeSet attrs) { | |
final TypedArray a = context.obtainStyledAttributes(attrs, new int [] { android.R.attr.listDivider }); | |
mDivider = a.getDrawable(0); | |
a.recycle(); | |
} | |
public DividerItemDecoration(Drawable divider) { mDivider = divider; } | |
@Override | |
public void getItemOffsets (Rect outRect, View view, RecyclerView parent, RecyclerView.State state) { | |
super.getItemOffsets(outRect, view, parent, state); | |
if (mDivider == null) return; | |
if (parent.getChildPosition(view) < 1) return; | |
if (getOrientation(parent) == LinearLayoutManager.VERTICAL) outRect.top = mDivider.getIntrinsicHeight(); | |
else outRect.left = mDivider.getIntrinsicWidth(); | |
} | |
@Override | |
public void onDrawOver(Canvas c, RecyclerView parent) { | |
if (mDivider == null) { super.onDrawOver(c, parent); return; } | |
if (getOrientation(parent) == LinearLayoutManager.VERTICAL) { | |
final int left = parent.getPaddingLeft(); | |
final int right = parent.getWidth() - parent.getPaddingRight(); | |
final int childCount = parent.getChildCount(); | |
for (int i=1; i < childCount; i++) { | |
final View child = parent.getChildAt(i); | |
final RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams(); | |
final int size = mDivider.getIntrinsicHeight(); | |
final int top = child.getTop() - params.topMargin; | |
final int bottom = top + size; | |
mDivider.setBounds(left, top, right, bottom); | |
mDivider.draw(c); | |
} | |
} else { //horizontal | |
final int top = parent.getPaddingTop(); | |
final int bottom = parent.getHeight() - parent.getPaddingBottom(); | |
final int childCount = parent.getChildCount(); | |
for (int i=1; i < childCount; i++) { | |
final View child = parent.getChildAt(i); | |
final RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams(); | |
final int size = mDivider.getIntrinsicWidth(); | |
final int left = child.getLeft() - params.leftMargin; | |
final int right = left + size; | |
mDivider.setBounds(left, top, right, bottom); | |
mDivider.draw(c); | |
} | |
} | |
} | |
private int getOrientation(RecyclerView parent) { | |
if (parent.getLayoutManager() instanceof LinearLayoutManager) { | |
LinearLayoutManager layoutManager = (LinearLayoutManager) parent.getLayoutManager(); | |
return layoutManager.getOrientation(); | |
} else throw new IllegalStateException("DividerItemDecoration can only be used with a LinearLayoutManager."); | |
} | |
} |
From what I can see this does not show a divider in the last position since you are not accounting for it in the getItemOffsets
method.
Unfortunately there is no way to tell if we are at the very last item since the RecyclerView only returns the current number of items on screen.
Great work, but how can I set the divider height?
Thank you
You can create a shape file with giving only one dimension in size depending on the orientation of recycler view . This way you can alter divider height or widht without changing the class code.
I used the below code for recycler view with horizontal scrolling.
Unfortunately, I get a double divider in between two rows of the RecyclerView
I comment out 50-52 lines, then "Show first divider" work.
How to show the last divider?
If i insert new item to top of the recycler view , there is no divider showing between first and second item.
Please edit
line 88: top = child.getTop() - params.topMargin - mDivider.getIntrinsicHeight();
line 91: left = child.getLeft() - params.leftMargin - mDivider.getIntrinsicWidth();
if not the divider drawn above each item may overlap the content
I've forked it and added support for reverseLayout option in LinearLayoutManager:
https://gist.github.com/ceskobassman/179a62e1be65c2275baf
All reported problems in comments are fixed here:
https://gist.github.com/zokipirlo/82336d89249e05bba5aa
Use getChildAdapterPosition
instead getChildPosition
because getChildPosition
is deprecated.
How to set left or right margin for the divider? Is there any way out?
When I toggle between different items, the last divider always redraws itself. Is this a bug?
Hey! Thanks for everything! Looking very good!
I get a double divider in between two rows of the RecyclerView
it is good. thank you buddy
Great.. Thanks dude....
Thanks for your code!
Can you let me know which license is used for distribution of this code?
I'd like to use this code for a commercial app so I need to check the license.
Happy coding! :)
Strange, but it adds additional spaces of the same width between items (so instead of 5 dp I have 10 dp width space). See another example in https://gist.github.com/johnwatsondev/720730cf6b8c59fa6abe4f31dbaf59d7.
Thanks, works great!