Skip to content

Instantly share code, notes, and snippets.

@samuel22gj
Last active April 26, 2018 07:06
Show Gist options
  • Save samuel22gj/c64aa4afa5f9d3ae1925a6d62b0cd72b to your computer and use it in GitHub Desktop.
Save samuel22gj/c64aa4afa5f9d3ae1925a6d62b0cd72b to your computer and use it in GitHub Desktop.
A RecyclerView.ItemDecoration that can add spacing divider between items.
/**
* SpacingDividerItemDecoration is a {@link RecyclerView.ItemDecoration} that can add space divider
* between items of a {@link android.support.v7.widget.LinearLayoutManager}. It supports both {@link #HORIZONTAL}
* and {@link #VERTICAL} orientations.
*/
public class SpacingDividerItemDecoration extends RecyclerView.ItemDecoration {
@IntDef({HORIZONTAL, VERTICAL})
@Retention(RetentionPolicy.SOURCE)
public @interface OrientationMode {}
public static final int HORIZONTAL = LinearLayout.HORIZONTAL;
public static final int VERTICAL = LinearLayout.VERTICAL;
@IntDef(flag = true, value = {SHOW_DIVIDER_NONE, SHOW_DIVIDER_BEGINNING, SHOW_DIVIDER_MIDDLE, SHOW_DIVIDER_END})
@Retention(RetentionPolicy.SOURCE)
public @interface DividerMode {}
public static final int SHOW_DIVIDER_NONE = 0;
public static final int SHOW_DIVIDER_BEGINNING = 1;
public static final int SHOW_DIVIDER_MIDDLE = 1 << 1;
public static final int SHOW_DIVIDER_END = 1 << 2;
private int mSpacing;
private int mShowDividers = SHOW_DIVIDER_MIDDLE;
private int mOrientation = VERTICAL;
public SpaceDividerItemDecoration(@OrientationMode int orientation) {
setOrientation(orientation);
}
public void setSpace(@IntRange(from = 0) int spacing) {
if (spacing < 0) {
throw new IllegalArgumentException("Invalid spacing. It should be equal or large than zero");
}
mSpacing = spacing;
}
public void setOrientation(@OrientationMode int orientation) {
if (orientation != HORIZONTAL && orientation != VERTICAL) {
throw new IllegalArgumentException("Invalid orientation. It should be either HORIZONTAL or VERTICAL");
}
mOrientation = orientation;
}
public void setShowDividers(@DividerMode int showDividers) {
if (showDividers == mShowDividers) {
return;
}
mShowDividers = showDividers;
}
@Override
public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
outRect.set(0, 0, 0, 0);
if (mShowDividers == SHOW_DIVIDER_NONE) {
return;
}
int itemPosition = parent.getChildAdapterPosition(view);
int itemCount = state.getItemCount();
if (itemPosition == RecyclerView.NO_POSITION || itemCount < 1) {
return;
}
if (itemPosition == 0 && (mShowDividers & SHOW_DIVIDER_BEGINNING) != 0) {
addBeginningSpacing(outRect);
}
if (itemPosition == itemCount - 1 && (mShowDividers & SHOW_DIVIDER_END) != 0) {
addEndSpacing(outRect);
}
if (itemCount > 1 && itemPosition != itemCount - 1 && (mShowDividers & SHOW_DIVIDER_MIDDLE) != 0) {
addMiddleSpacing(outRect);
}
}
/**
* Add spacing at top or left base on orientation.
*
* @param outRect Rect to receive the output.
*/
private void addBeginningSpacing(Rect outRect) {
if (mOrientation == VERTICAL) {
outRect.top = mSpacing;
} else {
outRect.left = mSpacing;
}
}
/**
* Add spacing at bottom or right base on orientation.
*
* @param outRect Rect to receive the output.
*/
private void addMiddleSpacing(Rect outRect) {
if (mOrientation == VERTICAL) {
outRect.bottom = mSpacing;
} else {
outRect.right = mSpacing;
}
}
/**
* Add spacing at bottom or right base on orientation.
*
* @param outRect Rect to receive the output.
*/
private void addEndSpacing(Rect outRect) {
// The logic and implement are same with addMiddleSpace().
addMiddleSpacing(outRect);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment