RecyclerView에서 항목 사이에 칸막이와 공백을 추가하는 방법은 무엇입니까?


938

다음은 dividerdividerHeight 매개 변수를 ListView사용하여 클래스 에서 이전에 수행 한 방법의 예입니다 .

<ListView
    android:id="@+id/activity_home_list_view"
    android:layout_width="match_parent" 
    android:layout_height="match_parent"
    android:divider="@android:color/transparent"
    android:dividerHeight="8dp"/>

그러나 나는 RecyclerView수업 에서 그러한 가능성을 보지 못합니다 .

<android.support.v7.widget.RecyclerView
    android:id="@+id/activity_home_recycler_view"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:scrollbars="vertical"/>

이 경우 여백을 정의하거나 사용자 정의 구분선보기를 목록 항목의 레이아웃에 직접 추가하거나 내 목표를 달성하는 더 좋은 방법이 있습니까?



@EyesClear 다른 xml <TextView /> 항목을 추가하고 동일한 활동 목록에 사용하십시오.
Amitsharma

7
지원 lib에는 클래스가 있으며 다음 com.homeretailgroup.argos.android.view.decorators.DividerItemDecoration과 같이 사용하십시오.mRecyclerView.addItemDecoration(new DividerItemDecoration(activity, LinearLayoutManager.VERTICAL));
fada21

수직 목록의 경우 목록 항목에 아래쪽 여백을 추가 할 수 있으며 분할 자로 사용할 수 있습니까?
resw67

가장 간단한 방법은 어댑터 행의 첫 번째 항목 주위에 위쪽 / 아래쪽 여백을 추가하는 것입니다. android : layout_marginBottom = "4dp". (부모 레이아웃에 여백을 추가해도 잘리지 않습니다.)
pstorli

답변:


1227

2016 년 10 월 업데이트

Android 지원 라이브러리 25.0.0 버전에서는 다음과 같은 DividerItemDecoration클래스가 도입되었습니다 .

DividerItemDecoration은의 항목 사이에 구분자로 사용될 수있는 RecyclerView.ItemDecoration입니다 LinearLayoutManager. 방향 HORIZONTALVERTICAL방향을 모두 지원합니다 .

용법:

DividerItemDecoration dividerItemDecoration = new DividerItemDecoration(recyclerView.getContext(),
    layoutManager.getOrientation());
recyclerView.addItemDecoration(dividerItemDecoration);

이전 답변

일부 답변은 이후 더 이상 사용되지 않거나 완벽한 솔루션을 제공하지 않는 방법을 사용하므로 짧은 최신 요약을 시도했습니다.


달리 ListViewRecyclerView클래스가 더 분할과 관련된 매개 변수가 없습니다. 대신 확장 할 필요가 ItemDecorationA, RecyclerView의 내부 클래스 :

ItemDecoration어댑터의 데이터 세트에서 특정 항목보기에 오프셋 특별 인출 및 레이아웃을 추가 할 수있는 응용 프로그램을 할 수 있습니다. 항목, 하이라이트, 시각적 그룹화 경계 등을 구분하는 데 유용합니다.

모든 ItemDecorations(의 항목을보기 전에, 그들이 추가 된 순서대로 그려집니다 onDraw()() 및 항목 후 onDrawOver (에 Canvas, RecyclerView, RecyclerView.State).

Vertical 간격 ItemDecoration

확장 ItemDecoration하고 공간 height을 매개 변수로 사용하는 사용자 지정 생성자를 추가 하고 getItemOffsets()메서드를 재정의하십시오 .

public class VerticalSpaceItemDecoration extends RecyclerView.ItemDecoration {

    private final int verticalSpaceHeight;

    public VerticalSpaceItemDecoration(int verticalSpaceHeight) {
        this.verticalSpaceHeight = verticalSpaceHeight;
    }

    @Override
    public void getItemOffsets(Rect outRect, View view, RecyclerView parent,
            RecyclerView.State state) {
        outRect.bottom = verticalSpaceHeight;
    }
}

마지막 항목 아래에 공백을 삽입하지 않으려면 다음 조건을 추가하십시오.

if (parent.getChildAdapterPosition(view) != parent.getAdapter().getItemCount() - 1) {
            outRect.bottom = verticalSpaceHeight;
}

참고 : 당신은 또한 수정할 수 outRect.top, outRect.leftoutRect.right원하는 효과에 대한 속성.

분할기 ItemDecoration

확장 ItemDecoration및 재정의 onDraw()방법 :

public class DividerItemDecoration extends RecyclerView.ItemDecoration {

    private static final int[] ATTRS = new int[]{android.R.attr.listDivider};

    private Drawable divider;

    /**
     * Default divider will be used
     */
    public DividerItemDecoration(Context context) {
        final TypedArray styledAttributes = context.obtainStyledAttributes(ATTRS);
        divider = styledAttributes.getDrawable(0);
        styledAttributes.recycle();
    }

    /**
     * Custom divider will be used
     */
    public DividerItemDecoration(Context context, int resId) {
        divider = ContextCompat.getDrawable(context, resId);
    }

    @Override
    public void onDraw(Canvas c, RecyclerView parent, RecyclerView.State state) {
        int left = parent.getPaddingLeft();
        int right = parent.getWidth() - parent.getPaddingRight();

        int childCount = parent.getChildCount();
        for (int i = 0; i < childCount; i++) {
            View child = parent.getChildAt(i);

            RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();

            int top = child.getBottom() + params.bottomMargin;
            int bottom = top + divider.getIntrinsicHeight();

            divider.setBounds(left, top, right, bottom);
            divider.draw(c);
        }
    }
}

기본 Android 디바이더 속성을 사용하는 첫 번째 생성자 또는 자체 드로어 블을 사용하는 두 번째 생성자를 호출 할 수 있습니다 (예 : drawable / divider.xml).

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
       android:shape="rectangle">
    <size android:height="1dp" />
    <solid android:color="#ff992900" />
</shape>

참고 : 항목 위에 구분선을 그리려면 onDrawOver()대신 메서드를 재정의하십시오 .

용법

새 클래스 add VerticalSpaceItemDecoration또는 DividerSpaceItemDecorationto 를 사용하려면 ( RecyclerViewonCreateView(): 조각의 메소드에서)

private static final int VERTICAL_ITEM_SPACE = 48;
private RecyclerView recyclerView;
private LinearLayoutManager linearLayoutManager;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
        Bundle savedInstanceState) {
    View rootView = inflater.inflate(R.layout.fragment_feed, container, false);

    recyclerView = (RecyclerView) rootView.findViewById(R.id.fragment_home_recycler_view);
    linearLayoutManager = new LinearLayoutManager(getActivity());
    recyclerView.setLayoutManager(linearLayoutManager);

    //add ItemDecoration
    recyclerView.addItemDecoration(new VerticalSpaceItemDecoration(VERTICAL_ITEM_SPACE));
    //or
    recyclerView.addItemDecoration(new DividerItemDecoration(getActivity()));
    //or
    recyclerView.addItemDecoration(
            new DividerItemDecoration(getActivity(), R.drawable.divider));

    recyclerView.setAdapter(...);

    return rootView;
}

아이템 장식 프로세스를 단순화 해야하는 Lucas Rocha의 라이브러리 도 있습니다 . 그래도 시도하지 않았습니다.

특징 중 하나 는 다음과 같습니다.

  • 다음을 포함한 재고 품목 장식 모음 :
  • 아이템 간격 가로 / 세로 칸막이.
  • 아이템 목록

3
@droppin_science 내가 틀렸다면 수정하지만에 개체를 만들지 않습니다 onDraw(). 방금 기존 인스턴스를 참조합니다.
EyesClear 0시 13 분에서

1
드로어 블을 만드는 대신 페인트를 사용하는 것이 좋은지 궁금합니다. 그럼 난 호출 할 수 canvas.drawLine(startX, startY, stopX, stopY, mPaint)있는 onDrawOver? 성능 차이가 있습니까?
Arst

1
유익한 설명 : 나중에 목록에 항목을 추가하려는 경우 항상 마지막 항목에 공백을 추가하십시오. 그렇게하지 않으면 항목을 추가 할 때 공백이 없습니다. VerticalSpace에 감사드립니다!
Tsuharesu

24
항목이 완전히 불투명 한 경우 위에 표시된 DividerItemDecoration이 작동하지 않으며, 구분선이 항목에 의해 오버라이드됩니다. 이 경우 getItemOffsets ()도 재정의하고 아래쪽 오프셋을 outRect에 추가하여 디바이더가 항목 외부로 끝나도록해야합니다. 또는 onDraw () 대신 onDrawOver ()를 재정 의하여 항목에 구분선을 그릴 수 있습니다.
jpop

115
recyclerView에 디바이더를 추가하는 전체 코드 페이지가 가장 좋습니다. 부끄러운 구글.
조심

480

그냥 추가

recyclerView.addItemDecoration(new DividerItemDecoration(getContext(),
                DividerItemDecoration.VERTICAL));

또한 종속성을 추가해야 할 수도 있습니다
compile 'com.android.support:recyclerview-v7:27.1.0'

편집하다:

약간 커스터마이징하기 위해 커스텀 드로어 블을 추가 할 수 있습니다.

DividerItemDecoration itemDecorator = new DividerItemDecoration(getContext(), DividerItemDecoration.VERTICAL);
itemDecorator.setDrawable(ContextCompat.getDrawable(getContext(), R.drawable.divider));

예를 들어, 사용자 정의 드로어 블을 자유롭게 사용할 수 있습니다.

<shape xmlns:android="http://schemas.android.com/apk/res/android"
       android:shape="rectangle">
    <solid android:color="@color/colorPrimary"/>
    <size android:height="0.5dp"/>
</shape>

활동이 필요하지 않습니다. 상황이 충분
mac229

정답이어야합니다. PLZ, getActivity를 컨텍스트로 변경하십시오.
존 프레디 트루 히요 오르테가

또한 LayoutManager에서 방향을 얻는 것이 좋습니다.
lsrom

감사합니다! 또한 Configuration수직 분배기에 사용할 수 있습니다 .if (orientation == Configuration.ORIENTATION_LANDSCAPE) { recyclerView.addItemDecoration(new DividerItemDecoration(this, DividerItemDecoration.HORIZONTAL)); } else { recyclerView.addItemDecoration(new DividerItemDecoration(this, DividerItemDecoration.VERTICAL));}
AlexS

3
좋은 대답이지만 마지막 항목 뒤에 분배기를 추가합니다.
CoolMind 2012 년

256

Alex Fu의 Github에있는이 특정 파일에주의를 기울일 수 있습니다 : https://gist.github.com/alexfu/0f464fc3742f134ccd1e

DividerItemDecoration.java 예제 파일 인 "지원 데모에서 곧바로 끌어 들였습니다"( https://plus.google.com/103498612790395592106/posts/VVEB3m7NkSS )

프로젝트 에서이 파일을 가져온 후 분할 선을 멋지게 가져 와서 재활용 자보기에 항목 장식으로 추가 할 수있었습니다.

다음은 Recyclerview를 포함하는 조각에서 onCreateView가 어떻게 보이는지 보여줍니다.

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    View rootView = inflater.inflate(R.layout.fragment_recycler_view, container, false);

    mRecyclerView = (RecyclerView) rootView.findViewById(R.id.my_recycler_view);
    mRecyclerView.addItemDecoration(new DividerItemDecoration(getActivity(), DividerItemDecoration.VERTICAL_LIST));

    mRecyclerView.setHasFixedSize(true);
    mLayoutManager = new LinearLayoutManager(getActivity());
    mRecyclerView.setLayoutManager(mLayoutManager);
    mRecyclerView.setItemAnimator(new DefaultItemAnimator());

    return rootView;
}

추가 스타일링을 할 수 있다고 확신하지만 시작점입니다. :)


"footerDividersEnabled", "headerDividersEnabled", "listSelector", "fastScrollEnabled", "smoothScrollbar", "textFilterEnabled"를 어떻게 추가합니까?
안드로이드 개발자

스타일링을 넣는 방법에 대한 의견이 있으십니까?
nizam.sp

스타일이 솔루션은 당신이 "안드로이드 : listDivider"오버라이드 (override) 할 필요가 테마에 속성
파벨 두드카

1
Divider는 RecyclerView에서 작동하지 않습니다. RecyclerView.itemDecoration을 사용해야합니다. 이 답변보기 : stackoverflow.com/a/27664023/2311451
Cocorico

3
분배기가 왜 품목의 전체 너비를 확장합니까? 어떻게 스펙처럼 표시 google.com/design/spec/components/lists.html#lists-specs

156

ItemDecoration모든 항목 사이에 동일한 공간을위한 간단한 구현.

public class SpacesItemDecoration extends RecyclerView.ItemDecoration {
    private int space;

    public SpacesItemDecoration(int space) {
        this.space = space;
    }

    @Override
    public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
        outRect.left = space;
        outRect.right = space;
        outRect.bottom = space;

        // Add top margin only for the first item to avoid double space between items
        if(parent.getChildAdapterPosition(view) == 0) {
            outRect.top = space;
        }
    }
}

나는 공간을 확보하고 있지만 어떻게 분배기를
얻는가

26
getChildPosition더 이상 사용되지 않으며 getChildAdapterPosition대신 사용할 수 있습니다.
EyesClear

4
에 대한 호출을 제거하는 것을 잊지 마십시오. 그렇지 않으면 super.getItemOffsets오프셋이 덮어 쓰기됩니다.
jayeffkay 2016 년

@EyesClear를 사용해서는 안 getChildLayoutPosition됩니까?
Avinash R

3
간격을 픽셀 단위로 구현합니까?
filthy_wizard

108

간단한 방법은 RecyclerView의 배경색과 항목의 다른 배경색을 설정하는 것입니다. 여기에 예가 있습니다 ...

<android.support.v7.widget.RecyclerView
    android:background="#ECEFF1"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:scrollbars="vertical"/>

그리고 텍스트 뷰의 항목은 하단 여백 "X"DP 또는 PX와 (그것은 아무것도하지만 될 수 있습니다).

<TextView
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_marginBottom="1dp"
    android:background="#FFFFFF"/>

출력 ...

여기에 이미지 설명을 입력하십시오


2
어떤 트릭! 로드하는 동안 목록을 흰색으로 유지하면됩니다.
Hamzeh Soboh

36
오버 드로우에주의하십시오!
shem

@ shem 당신은 정교한 수 있습니까?
RominaV

7
Android에서 여러 레이어를 레이어 위에 그릴 때 (활동 배경, 재활용보기 배경 및 항목보기 배경)-Android는 사용자에게 보이지 않는 모든 레이어를 그립니다. 오버 드로 (overdraw)라고 불리며 성능에 영향을 줄 수 있습니다. youtube.com/watch?v=T52v50r-JfE
shem

41

간단한 구분선을 사용

하면 각 항목에 구분선을 추가하는 데 도움이 될 것이라고 생각합니다 .
1- 드로어 블 디렉토리에 추가하십시오 line_divider.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<size
    android:width="1dp"
    android:height="1dp" />
<solid android:color="#999999" />
</shape>

2- SimpleDividerItemDecoration 클래스 만들기이
예제를 사용하여이 클래스를 정의했습니다.
https://gist.github.com/polbins/e37206fbc444207c0e92

package com.example.myapp;
import android.content.Context;
import android.content.res.Resources;
import android.graphics.Canvas;
import android.graphics.drawable.Drawable;
import android.support.v7.widget.RecyclerView;
import android.view.View;
import com.example.myapp.R;

public class SimpleDividerItemDecoration extends RecyclerView.ItemDecoration{
private Drawable mDivider;

public SimpleDividerItemDecoration(Resources resources) {
    mDivider = resources.getDrawable(R.drawable.line_divider);
}

public void onDrawOver(Canvas c, RecyclerView parent, RecyclerView.State state) {
    int left = parent.getPaddingLeft();
    int right = parent.getWidth() - parent.getPaddingRight();

    int childCount = parent.getChildCount();
    for (int i = 0; i < childCount; i++) {
        View child = parent.getChildAt(i);

        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();

        int top = child.getBottom() + params.bottomMargin;
        int bottom = top + mDivider.getIntrinsicHeight();

        mDivider.setBounds(left, top, right, bottom);
        mDivider.draw(c);
    }
  }
}


3- RecyclerView를 사용하는 활동 또는 조각에서 onCreateView 내부에 다음을 추가하십시오.

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
 RecyclerView myRecyclerView = (RecyclerView) layout.findViewById(R.id.my_recycler_view);
 myRecyclerView.addItemDecoration(new SimpleDividerItemDecoration(getResources()));
 ....
 }


4- 아이템 사이에 간격을 추가하려면
아이템 뷰에 패딩 속성을 추가하면됩니다.

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent" android:layout_height="match_parent"
android:padding="4dp"
>
..... item structure
</RelativeLayout>

셀 사이에 세로 구분선을 표시하기 위해 GridLayoutManager에서 어떻게 작동합니까?
안드로이드 개발자

2
resources.getDrawable ()은 더 이상 사용되지 않습니다. 컨텍스트를 전달하고 ContextCompat.getDrawable (context, R.drawable.line_divider)을 사용할 수 있습니다
Eric B.

36

내가 설정 한대로 ItemAnimators. 는 ItemDecorator입력하거나 애니메이션과 함께 종료되지 않습니다.

각 항목의 항목보기 레이아웃 파일에보기 줄이 생겼습니다. 내 사건을 해결했다. DividerItemDecoration단순한 분배기에는 너무 많은 마법이 느껴졌습니다.

<View
    android:layout_width="match_parent"
    android:layout_height="1px"
    android:layout_marginLeft="5dp"
    android:layout_marginRight="5dp"
    android:background="@color/lt_gray"/>

네 말이 맞아 애니메이션은 ItemDecoration에서 작동하지 않습니다. 왜 그런지 잘 모르겠지만 아무 것도 지정하지 않으면 애니메이션이 표시되고 ItemDecoration으로 만든 선이 따르지 않는 것이 매우 산만하고 추악합니다. 그래서 나는 당신과 같은 해결책을 사용할 것입니다.
Michel

마지막 항목은 어떻게 다루었습니까?
oldergod

@oldergod. 당신은 오른쪽 통증 포인트를 지적했다. 먼저 마지막 항목에 디바이더가있는 디자인에 동의합니다. 그러나 당신이 그것을 원하지 않는다면. 이 뷰에 ID를 할당하고 위치가 마지막 인 경우 bindView에서 숨 깁니다.
Javanator

@Javanator 나는 내가했던 것과 같은 접근 방식을 확인했다. 감사.
oldergod

가장 간단한 것이 최고입니다
hyyou2010

27

이것은 간단합니다. 복잡한 코드가 필요하지 않습니다.

DividerItemDecoration divider = new 
DividerItemDecoration(mRVMovieReview.getContext(), 
DividerItemDecoration.VERTICAL);
divider.setDrawable(
    ContextCompat.getDrawable(getBaseContext(), R.drawable.line_divider)
);
mRVMovieReview.addItemDecoration(divider);

드로어 블에 이것을 추가하십시오 : line_divider.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" 
  android:shape="rectangle">
    <size android:height="1dp" />
    <solid android:color="@android:color/black" />
</shape>

21

머티리얼 디자인을 사용하여이를 올바르게 구현할 수있는 올바른 방법이 없기 때문에리스트 아이템에 직접 분배기를 추가하기 위해 다음과 같은 트릭을 수행했습니다.

<View
android:layout_width="match_parent"
android:layout_height="1dp"
android:background="@color/dividerColor"/>

재료 설계에 대한 고도 정보를받은 후 DividerItemDecoration이 작동을 멈 춥니 다 (Inbox와 같은 효과를 얻기 위해). 간단한 것은 너무 복잡해졌습니다. 이 솔루션은 간단하고 작동합니다.
DenisGL

21

Divider보기와 Divider Insets를 처리하는 방법은 RecyclerView 확장을 추가하는 것입니다.

1.

View 또는 RecyclerView의 이름을 지정하여 새 확장 파일을 추가하십시오.

RecyclerViewExtension.kt

setDividerRecyclerViewExtension.kt 파일 내에 확장 메소드를 추가 하십시오.

/*
* RecyclerViewExtension.kt
* */
import androidx.annotation.DrawableRes
import androidx.core.content.ContextCompat
import androidx.recyclerview.widget.DividerItemDecoration
import androidx.recyclerview.widget.RecyclerView


fun RecyclerView.setDivider(@DrawableRes drawableRes: Int) {
    val divider = DividerItemDecoration(
        this.context,
        DividerItemDecoration.VERTICAL
    )
    val drawable = ContextCompat.getDrawable(
        this.context,
        drawableRes
    )
    drawable?.let {
        divider.setDrawable(it)
        addItemDecoration(divider)
    }
}

2.

drawable패키지 내에 Drawable 리소스 파일을 recycler_view_divider.xml다음 과 같이 만듭니다 .

<inset xmlns:android="http://schemas.android.com/apk/res/android"
    android:insetLeft="10dp"
    android:insetRight="10dp">

    <shape>
        <size android:height="0.5dp" />
        <solid android:color="@android:color/darker_gray" />
    </shape>

</inset>

위치를 왼쪽과 오른쪽 지정할 수 있습니다 마진android:insetLeftandroid:insetRight.

삼.

RecyclerView가 초기화 된 활동 또는 조각에서 다음을 호출하여 사용자 정의 드로어 블을 설정할 수 있습니다.

recyclerView.setDivider(R.drawable.recycler_view_divider)

4.

건배 🍺

분배기가있는 RecyclerView 행.


16

누구든지 항목 사이에 10dp 간격을 추가하려는 경우 drawable을 DividerItemDecoration다음과 같이 설정하면됩니다 .

DividerItemDecoration dividerItemDecoration = new DividerItemDecoration(
    recyclerView.getContext(),
    layoutManager.getOrientation()
);

dividerItemDecoration.setDrawable(
    ContextCompat.getDrawable(getContext(), R.drawable.divider_10dp)
); 

다음을 divider_10dp포함하는 드로어 블 리소스는 어디에 있습니까?

<shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="rectangle">
    <size android:height="10dp"/>
    <solid android:color="@android:color/transparent"/>
</shape>



11

단지를 찾고있는 사람들을 위해 항목 사이에 공백RecyclerView당신은 내가 더 큰 패딩을 준 첫 번째와 마지막 항목을 제외한 모든 항목과 동일한 공간을 얻을 내 접근 방식을 참조하십시오. 왼쪽 / 오른쪽 가로 LayoutManager및 위쪽 / 아래쪽 세로 에만 패딩을 적용 LayoutManager합니다.

public class PaddingItemDecoration extends RecyclerView.ItemDecoration {

    private int mPaddingPx;
    private int mPaddingEdgesPx;

    public PaddingItemDecoration(Activity activity) {
        final Resources resources = activity.getResources();
        mPaddingPx = (int) resources.getDimension(R.dimen.paddingItemDecorationDefault);
        mPaddingEdgesPx = (int) resources.getDimension(R.dimen.paddingItemDecorationEdge);
    }

    @Override
    public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
        super.getItemOffsets(outRect, view, parent, state);

        final int itemPosition = parent.getChildAdapterPosition(view);
        if (itemPosition == RecyclerView.NO_POSITION) {
            return;
        }
        int orientation = getOrientation(parent);
        final int itemCount = state.getItemCount();

        int left = 0;
        int top = 0;
        int right = 0;
        int bottom = 0;

        /** HORIZONTAL */
        if (orientation == LinearLayoutManager.HORIZONTAL) {
            /** all positions */
            left = mPaddingPx;
            right = mPaddingPx;

            /** first position */
            if (itemPosition == 0) {
                left += mPaddingEdgesPx;
            }
            /** last position */
            else if (itemCount > 0 && itemPosition == itemCount - 1) {
                right += mPaddingEdgesPx;
            }
        }
        /** VERTICAL */
        else {
            /** all positions */
            top = mPaddingPx;
            bottom = mPaddingPx;

            /** first position */
            if (itemPosition == 0) {
                top += mPaddingEdgesPx;
            }
            /** last position */
            else if (itemCount > 0 && itemPosition == itemCount - 1) {
                bottom += mPaddingEdgesPx;
            }
        }

        if (!isReverseLayout(parent)) {
            outRect.set(left, top, right, bottom);
        } else {
            outRect.set(right, bottom, left, top);
        }
    }

    private boolean isReverseLayout(RecyclerView parent) {
        if (parent.getLayoutManager() instanceof LinearLayoutManager) {
            LinearLayoutManager layoutManager = (LinearLayoutManager) parent.getLayoutManager();
            return layoutManager.getReverseLayout();
        } else {
            throw new IllegalStateException("PaddingItemDecoration can only be used with a LinearLayoutManager.");
        }
    }

    private int getOrientation(RecyclerView parent) {
        if (parent.getLayoutManager() instanceof LinearLayoutManager) {
            LinearLayoutManager layoutManager = (LinearLayoutManager) parent.getLayoutManager();
            return layoutManager.getOrientation();
        } else {
            throw new IllegalStateException("PaddingItemDecoration can only be used with a LinearLayoutManager.");
        }
    }
}

dimens.xml

<resources>
    <dimen name="paddingItemDecorationDefault">10dp</dimen>
    <dimen name="paddingItemDecorationEdge">20dp</dimen>
</resources>

11

당신의 견해에 여백을 추가하면 그것은 나를 위해 일했습니다.

android:layout_marginTop="10dp"

동일한 간격 을 추가 하고 XML로 하려는 경우에 팽창하는 항목에 대해 동일한 양을 설정 padding하고 배경색이 간격 색상을 결정하도록합니다.RecyclerViewlayoutMarginRecyclerView


3
이것이 효과가 있지만, 이것은 정답이 아닙니다. 예를 들어, 이것은 행 레이아웃에 추가 작업을 수행하지 않고 문제를 해결하지 못하기 때문에 상단에 여백 x1이 나타나고 행 사이에 여백 x2가 나타납니다.
Sreekanth Karumanaghat

overscroll패딩을 적용 할 때 목록의 끝을 당기는 효과에 불필요한 패딩이 적용 되기 때문에 이것은 좋은 생각이 아닙니다.RecyclerView
AeroEchelon

지원 라이브러리 CardView에서 항목 레이아웃을 래핑하는 것이 높이 / 그림자 등과 같은 다른 속성을 제어 할 수 있도록하는 것이 좋습니다. <?xml version="1.0" encoding="utf-8"?> <android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android" xmlns:card_view="http://schemas.android.com/apk/res-auto" android:id="@+id/card_view" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginBottom="10dp" card_view:cardElevation="4dp" <!-- your item's XML here --> </android.support.v7.widget.CardView>
kip2

11
  • 여기에 분배기를 추가하는 간단한 해킹이 있습니다.
  • 다음과 같이 재활용품 항목의 레이아웃에 배경을 추가하십시오.

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@drawable/shape_border"
        android:gravity="center"
        android:orientation="horizontal"
        android:padding="5dp">
    
    <ImageView
        android:id="@+id/imageViewContactLogo"
        android:layout_width="60dp"
        android:layout_height="60dp"
        android:layout_marginRight="10dp"
        android:src="@drawable/ic_user" />
    
    <LinearLayout
        android:id="@+id/linearLayout"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_weight="0.92"
        android:gravity="center|start"
        android:orientation="vertical">
    
    <TextView
        android:id="@+id/textViewContactName"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:singleLine="true"
        android:text="Large Text"
        android:textAppearance="?android:attr/textAppearanceLarge" />
    
    <TextView
        android:id="@+id/textViewStatusOrNumber"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="5dp"
        android:singleLine="true"
        android:text=""
        android:textAppearance="?android:attr/textAppearanceMedium" />
    </LinearLayout>
    
    <TextView
        android:id="@+id/textViewUnreadCount"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginRight="10dp"
        android:padding="5dp"
        android:text=""
        android:textAppearance="?android:attr/textAppearanceMedium"
        android:textColor="@color/red"
        android:textSize="22sp" />
    
    <Button
        android:id="@+id/buttonInvite"
        android:layout_width="54dp"
        android:layout_height="wrap_content"
        android:background="@drawable/ic_add_friend" />
    </LinearLayout>

드로어 블 폴더에 다음 shape_border.xml을 작성하십시오.

  <?xml version="1.0" encoding="utf-8"?>
    <shape xmlns:android="http://schemas.android.com/apk/res/android"
      android:shape="rectangle" >
       <gradient
        android:angle="270"
        android:centerColor="@android:color/transparent"
        android:centerX="0.01"
        android:startColor="#000" />
    </shape>

최종 결과는 분배기가있는 RecyclerView입니다.

최종 결과는 분배기가있는 RecyclerView입니다.


1
이것은 바람직한 접근 방식이 아닙니다. @EyesClear 응답 동수가 된 onDraw에서의를 int로하고 있지만 parent.getChildAdapterPosition(view) != parent.getAdapter().getItemCount() - 1아마해야 parent.getChildAdapterPosition(view) > 0으로 outRect.bottom = mVerticalSpaceHeight되는 outRect.top = mVerticalSpaceHeight것이 허용 대답해야합니다.
droppin_science

@droppin_science-선호하는 접근 방식이 아니라고 생각하여 무시할 수는 없습니다. 예상 한대로 정확한 결과를 얻습니다. 또한 EyesClear의 답변을 보지만 그 대답은 간단한 분배기로 너무 복잡합니다. 항목으로 여분의 장식을하면 허용되는 답변이 될 수 있습니다.
turbandroid

다운 유권자들에게이 답변은 DividerItemDecoration에 대한 공식 수업이 없을 때 제공되었으므로이 답변과 Leo Droidcoder가 제공 한 다음 답변 사이의 시간 간격을 비교하십시오. :)
turbandroid

9

나는 이전 요점에서 DividerItemDecoration을 포크하고 사용 사례에 맞게 단순화했으며 마지막 목록 항목 뒤의 분배자를 포함하여 ListView에서 그려진 방식으로 분배기를 그리도록 수정했습니다. 세로 ItemAnimator 애니메이션도 처리합니다.

1)이 클래스를 프로젝트에 추가하십시오.

public class DividerItemDecoration extends RecyclerView.ItemDecoration {
    private static final int[] ATTRS = new int[]{android.R.attr.listDivider};
    private Drawable divider;

    public DividerItemDecoration(Context context) {
        try {
            final TypedArray a = context.obtainStyledAttributes(ATTRS);
            divider = a.getDrawable(0);
            a.recycle();
        } catch (Resources.NotFoundException e) {
            // TODO Log or handle as necessary.
        }
    }

    @Override
    public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
        super.getItemOffsets(outRect, view, parent, state);
        if (divider == null) return;
        if (parent.getChildAdapterPosition(view) < 1) return;

        if (getOrientation(parent) == LinearLayoutManager.VERTICAL)
            outRect.top = divider.getIntrinsicHeight();
        else
            throw new IllegalArgumentException("Only usable with vertical lists");
    }

    @Override
    public void onDrawOver(Canvas c, RecyclerView parent, RecyclerView.State state) {
        if (divider == null) {
            super.onDrawOver(c, parent, state);
            return;
        }

        final int left = parent.getPaddingLeft();
        final int right = parent.getWidth() - parent.getPaddingRight();
        final int childCount = parent.getChildCount();

        for (int i = 0; i < childCount; ++i) {
            final View child = parent.getChildAt(i);
            final RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();
            final int size = divider.getIntrinsicHeight();
            final int top = (int) (child.getTop() - params.topMargin - size + child.getTranslationY());
            final int bottom = top + size;
            divider.setBounds(left, top, right, bottom);
            divider.draw(c);

            if (i == childCount - 1) {
                final int newTop = (int) (child.getBottom() + params.bottomMargin + child.getTranslationY());
                final int newBottom = newTop + size;
                divider.setBounds(left, newTop, right, newBottom);
                divider.draw(c);
            }
        }
    }

    private int getOrientation(RecyclerView parent) {
        if (!(parent.getLayoutManager() instanceof LinearLayoutManager))
            throw new IllegalStateException("Layout manager must be an instance of LinearLayoutManager");
        return ((LinearLayoutManager) parent.getLayoutManager()).getOrientation();
    }
}

2) RecylerView에 데코레이터를 추가하십시오.

recyclerView.addItemDecoration(new DividerItemDecoration(getActivity()));

맞습니다. LinearLayoutManager를위한 것입니다. 아이디어를 가져와 GridLayoutManager에 적용 할 수 있습니다.
OpenGL ES 배우기

8

shape xml구분선 높이와 색상을 변경 하기 위해 를 만드는 대신 . 프로그래밍 방식으로 만들 수 있습니다

val divider = DividerItemDecoration(context,
        DividerItemDecoration.VERTICAL)

divider.setDrawable(ShapeDrawable().apply {
    intrinsicHeight = resources.getDimensionPixelOffset(R.dimen.dp_15)
    paint.color = Color.RED // note: currently (support version 28.0.0), we can not use tranparent color here, if we use transparent, we still see a small divider line. So if we want to display transparent space, we can set color = background color or we can create a custom ItemDecoration instead of DividerItemDecoration. 
})

recycler_devices.addItemDecoration(divider)

이것은 유용한 답변입니다
taha

7

Google 검색에서 가져온ItemDecoration 을 다음에 추가 하십시오 RecyclerView.

public class DividerItemDecoration extends RecyclerView.ItemDecoration {

private Drawable mDivider;
private boolean mShowFirstDivider = false;
private boolean mShowLastDivider = false;


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(Context context, AttributeSet attrs, boolean showFirstDivider,
        boolean showLastDivider) {
    this(context, attrs);
    mShowFirstDivider = showFirstDivider;
    mShowLastDivider = showLastDivider;
}

public DividerItemDecoration(Drawable divider) {
    mDivider = divider;
}

public DividerItemDecoration(Drawable divider, boolean showFirstDivider,
        boolean showLastDivider) {
    this(divider);
    mShowFirstDivider = showFirstDivider;
    mShowLastDivider = showLastDivider;
}

@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, RecyclerView.State state) {
    if (mDivider == null) {
        super.onDrawOver(c, parent, state);
        return;
    }

    // Initialization needed to avoid compiler warning
    int left = 0, right = 0, top = 0, bottom = 0, size;
    int orientation = getOrientation(parent);
    int childCount = parent.getChildCount();

    if (orientation == LinearLayoutManager.VERTICAL) {
        size = mDivider.getIntrinsicHeight();
        left = parent.getPaddingLeft();
        right = parent.getWidth() - parent.getPaddingRight();
    } else { //horizontal
        size = mDivider.getIntrinsicWidth();
        top = parent.getPaddingTop();
        bottom = parent.getHeight() - parent.getPaddingBottom();
    }

    for (int i = mShowFirstDivider ? 0 : 1; i < childCount; i++) {
        View child = parent.getChildAt(i);
        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();

        if (orientation == LinearLayoutManager.VERTICAL) {
            top = child.getTop() - params.topMargin;
            bottom = top + size;
        } else { //horizontal
            left = child.getLeft() - params.leftMargin;
            right = left + size;
        }
        mDivider.setBounds(left, top, right, bottom);
        mDivider.draw(c);
    }

    // show last divider
    if (mShowLastDivider && childCount > 0) {
        View child = parent.getChildAt(childCount - 1);
        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();
        if (orientation == LinearLayoutManager.VERTICAL) {
            top = child.getBottom() + params.bottomMargin;
            bottom = top + size;
        } else { // horizontal
            left = child.getRight() + params.rightMargin;
            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.");
    }
}
}

이것은 LinearLayoutManager에만 적합합니다. GridLayoutManager를 위해 무엇을해야합니까?
안드로이드 개발자

6

이 링크는 저에게 매력처럼 작용했습니다.

https://gist.github.com/lapastillaroja/858caf1a82791b6c1a36

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.util.AttributeSet;
import android.view.View;

public class DividerItemDecoration extends RecyclerView.ItemDecoration {

    private Drawable mDivider;
    private boolean mShowFirstDivider = false;
    private boolean mShowLastDivider = false;


    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(Context context, AttributeSet attrs, boolean showFirstDivider,
            boolean showLastDivider) {
        this(context, attrs);
        mShowFirstDivider = showFirstDivider;
        mShowLastDivider = showLastDivider;
    }

    public DividerItemDecoration(Drawable divider) {
        mDivider = divider;
    }

    public DividerItemDecoration(Drawable divider, boolean showFirstDivider,
            boolean showLastDivider) {
        this(divider);
        mShowFirstDivider = showFirstDivider;
        mShowLastDivider = showLastDivider;
    }

    @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, RecyclerView.State state) {
        if (mDivider == null) {
            super.onDrawOver(c, parent, state);
            return;
        }

        // Initialization needed to avoid compiler warning
        int left = 0, right = 0, top = 0, bottom = 0, size;
        int orientation = getOrientation(parent);
        int childCount = parent.getChildCount();

        if (orientation == LinearLayoutManager.VERTICAL) {
            size = mDivider.getIntrinsicHeight();
            left = parent.getPaddingLeft();
            right = parent.getWidth() - parent.getPaddingRight();
        } else { //horizontal
            size = mDivider.getIntrinsicWidth();
            top = parent.getPaddingTop();
            bottom = parent.getHeight() - parent.getPaddingBottom();
        }

        for (int i = mShowFirstDivider ? 0 : 1; i < childCount; i++) {
            View child = parent.getChildAt(i);
            RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();

            if (orientation == LinearLayoutManager.VERTICAL) {
                top = child.getTop() - params.topMargin;
                bottom = top + size;
            } else { //horizontal
                left = child.getLeft() - params.leftMargin;
                right = left + size;
            }
            mDivider.setBounds(left, top, right, bottom);
            mDivider.draw(c);
        }

        // show last divider
        if (mShowLastDivider && childCount > 0) {
            View child = parent.getChildAt(childCount - 1);
            RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();
            if (orientation == LinearLayoutManager.VERTICAL) {
                top = child.getBottom() + params.bottomMargin;
                bottom = top + size;
            } else { // horizontal
                left = child.getRight() + params.rightMargin;
                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.");
        }
    }
}

그런 다음 활동에서 :

mCategoryRecyclerView.addItemDecoration(
    new DividerItemDecoration(this, null));

또는 조각을 사용하는 경우 :

mCategoryRecyclerView.addItemDecoration(
    new DividerItemDecoration(getActivity(), null));

1
이것은 잘 작동하지만 목록의 마지막 항목 아래에 구분선이 표시되지 않습니다. 나는 이것이 필요하다 : mShowFirstDivider = false,, mShowLastDivider = true작동하지 않습니다. 왜 그런지 알아?

GridLayoutManager를 잘 처리 할 수 ​​없습니다.
안드로이드 개발자

6

우리는 DividerItemDecoration과 같은 recyclerview에 연결된 다양한 데코레이터를 사용하여 항목을 장식 할 수 있습니다.

EyesClear 의 답변에서 가져온 다음을 간단히 사용하십시오.

public class DividerItemDecoration extends RecyclerView.ItemDecoration {

private static final int[] ATTRS = new int[]{android.R.attr.listDivider};

private Drawable mDivider;

/**
 * Default divider will be used
 */
public DividerItemDecoration(Context context) {
    final TypedArray styledAttributes = context.obtainStyledAttributes(ATTRS);
    mDivider = styledAttributes.getDrawable(0);
    styledAttributes.recycle();
}

/**
 * Custom divider will be used
 */
public DividerItemDecoration(Context context, int resId) {
    mDivider = ContextCompat.getDrawable(context, resId);
}

@Override
public void onDraw(Canvas c, RecyclerView parent, RecyclerView.State state) {
    int left = parent.getPaddingLeft();
    int right = parent.getWidth() - parent.getPaddingRight();

    int childCount = parent.getChildCount();
    for (int i = 0; i < childCount; i++) {
        View child = parent.getChildAt(i);

        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();

        int top = child.getBottom() + params.bottomMargin;
        int bottom = top + mDivider.getIntrinsicHeight();

        mDivider.setBounds(left, top, right, bottom);
        mDivider.draw(c);
    }
}

} 그런 다음 위와 같이 사용하십시오

RecyclerView.ItemDecoration itemDecoration = new DividerItemDecoration(this, DividerItemDecoration.VERTICAL_LIST);
recyclerView.addItemDecoration(itemDecoration);

그러면 아래와 같이 목록의 각 항목 사이에 구분선이 표시됩니다.

여기에 이미지 설명을 입력하십시오

자세한 내용을 원하는 사용자는이 안내서 를 참조하십시오. RecyclerView 사용 _ CodePath Android Cliffnotes

여기에 몇 가지 대답은 여백 사용을 제안하지만 캐치는 다음과 같습니다. 상단 및 하단 여백을 모두 추가하면 항목 사이에 추가 된 것으로 나타나고 너무 큽니다. 둘 중 하나만 추가하면 전체 목록의 맨 위나 맨 아래에 여백이 없습니다. 상단에 거리의 절반을 추가하고 하단에 절반을 추가하면 외부 여백이 너무 작아집니다.

따라서 심미적으로 올바른 유일한 해결책은 시스템이 항목을 적절하게 적용 할 위치를 알고있는 항목입니다.

아래 의견에 의심이 있으면 알려주십시오. :)


1
이것은 DividerItemDecoration코드의 모양을 보여 주지 않습니다 .
IgorGanapolsky

1
그것의 AOSP 클래스, 난 당신을 위해 코드를 파고 ..... gist.githubusercontent.com/alexfu/0f464fc3742f134ccd1e/raw/…
Anudeep Samaiya

그것은 서로 다른 높이의 행을 처리하지 않으며, 그것은 그리드 수직 분할 표시되지 않습니다 : 그것은 잘 작동하지 않습니다
안드로이드 개발자

5

너무 늦었지만 GridLayoutManager이것을 사용합니다.

public class GridSpacesItemDecoration : RecyclerView.ItemDecoration
{
    private int space;

    public GridSpacesItemDecoration(int space) {
        this.space = space;
    }

    public override void GetItemOffsets(Android.Graphics.Rect outRect, View view, RecyclerView parent, RecyclerView.State state)
    {
        var position = parent.GetChildLayoutPosition(view);

        /// Only for GridLayoutManager Layouts
        var manager = parent.GetLayoutManager() as GridLayoutManager;

        if (parent.GetChildLayoutPosition(view) < manager.SpanCount)
            outRect.Top = space;

        if (position % 2 != 0) {
            outRect.Right = space;
        }

        outRect.Left = space;
        outRect.Bottom = space;
    }
}

이것은 당신이 가진 모든 스팬 수에 적용됩니다.

올리


상단 공간에 대해서는 어떻게 지원 FlexboxLayoutManager합니까?
안드로이드 개발자

5

프로그래밍 방식으로 쉽게 추가 할 수 있습니다.

레이아웃 관리자가 Linearlayout 인 경우 다음을 사용할 수 있습니다.

DividerItemDecoration은 LinearLayoutManager의 항목 간 분배기로 사용할 수있는 RecyclerView.ItemDecoration입니다. 수평 및 수직 방향을 모두 지원합니다.

 mDividerItemDecoration = new DividerItemDecoration(recyclerView.getContext(),
         mLayoutManager.getOrientation());
 recyclerView.addItemDecoration(mDividerItemDecoration);

출처


5

XML을 사용하지 않는 간단한 코드 기반 답변이 필요하다고 생각합니다.

DividerItemDecoration dividerItemDecoration = new DividerItemDecoration(recyclerView.getContext(), DividerItemDecoration.VERTICAL);

ShapeDrawable shapeDrawableForDivider = new ShapeDrawable(new RectShape());

int dividerThickness = // (int) (SomeOtherView.getHeight() * desiredPercent);
shapeDrawableForDivider.setIntrinsicHeight(dividerThickness);
shapeDrawableForDivider.setAlpha(0);

dividerItemDecoration.setDrawable(shapeDrawableForDivider);

recyclerView.addItemDecoration(dividerItemDecoration);

4

항목에 동일한 공간을 추가하려면 가장 간단한 방법은 카드 항목에 RecycleView에 대한 위쪽 + 왼쪽 여백과 오른쪽 + 아래쪽 여백을 추가하는 것입니다.

dimens.xml

<resources>
    <dimen name="divider">1dp</dimen>
</resources>

list_item.xml

<CardView
 android:layout_marginBottom="@dimen/divider"
 android:layout_marginRight="@dimen/divider">
 ...
</CardView>

list.xml

<RecyclerView
 android:paddingLeft="@dimen/divider"
 android:paddingTop="@dimen/divider"
/>

4

아래와 같이 목록 항목에 줄을 추가했습니다.

<View
android:id="@+id/divider"
android:layout_width="match_parent"
android:layout_height="1px"
android:background="@color/dividerColor"/>

1px는가는 선을 그립니다.

마지막 행의 디바이더를 숨기려면 divider.setVisiblity(View.GONE);마지막 목록 항목의 onBindViewHolder에서.


1
나는 이것을 선호한다. 다른 사람들은 너무 복잡하다.
Sam Chen

3

RecyclerView로부터 조금 다르다 ListView. 실제로, 같은 구조가 RecyclerView필요 ListView합니다. 예를 들어 LinearLayout. 는 LinearLayout(가)의 각 요소를 구분하는 파라미터를 갖는다. 아래 코드에서 나는 내부 RecyclerViewCardView객체 로 구성되어 있습니다.LinearLayout 에는 항목 사이에 약간의 공간을 두는 "패딩"이있는 되어 있습니다. 그 공간을 정말로 작게 만들고 선을 얻으십시오.

recyclerview_layout.xml의 Recycler보기는 다음과 같습니다.

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
    android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".ToDoList">

    <!-- A RecyclerView with some commonly used attributes -->
    <android.support.v7.widget.RecyclerView
        android:id="@+id/todo_recycler_view"
        android:scrollbars="vertical"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</RelativeLayout>

그리고 여기에 다른 파일에있는 각 항목의 모양이 있습니다 (그리고 모든 것을 둘러싼 LinearLayout의 android : padding 때문에 나누어 표시됨) : cards_layout.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical" android:layout_width="match_parent"
    android:layout_height="match_parent"
    **android:padding="@dimen/activity_vertical_margin"**>
    <!-- A CardView that contains a TextView -->
    <android.support.v7.widget.CardView
        xmlns:card_view="http://schemas.android.com/apk/res-auto"
        android:id="@+id/card_view"
        android:layout_gravity="center"
        android:layout_width="match_parent"
        android:layout_height="100dp"
        android:elevation="30dp"
        card_view:cardElevation="3dp">
            <TextView
                android:id="@+id/info_text"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                />
    </android.support.v7.widget.CardView>
</LinearLayout>

3

정말 쉬운 해결책은 RecyclerView-FlexibleDivider 를 사용하는 것입니다

의존성 추가 :

compile 'com.yqritc:recyclerview-flexibledivider:1.4.0'

recyclerview에 추가하십시오.

recyclerView.addItemDecoration(new HorizontalDividerItemDecoration.Builder(context).build());

그리고 당신은 끝났습니다!


매력처럼 작동합니다 ... 오픈 소스 공유를 좋아해야합니다.
Billy

3

1. 방법 중 하나는 cardview와 recycler view를 함께 사용하면 디바이더와 같은 효과를 쉽게 추가 할 수 있습니다. 전의. https://developer.android.com/training/material/lists-cards.html

2. 다른 하나는 뷰를 리사이클 러보기의 list_item_layout에 분배기로 추가하는 것 입니다.

        <View
            android:id="@+id/view1"
            android:layout_width="match_parent"
            android:layout_height="1dp"
            android:background="@color/colorAccent" />

3
public class CommonItemSpaceDecoration extends RecyclerView.ItemDecoration {

        private int mSpace = 0;
        private boolean mVerticalOrientation = true;

    public CommonItemSpaceDecoration(int space) {
        this.mSpace = space;
    }

    public CommonItemSpaceDecoration(int space, boolean verticalOrientation) {
        this.mSpace = space;
        this.mVerticalOrientation = verticalOrientation;
    }

    @Override
    public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
        outRect.top = SizeUtils.dp2px(view.getContext(), mSpace);
        if (mVerticalOrientation) {
            if (parent.getChildAdapterPosition(view) == 0) {
                outRect.set(0, SizeUtils.dp2px(view.getContext(), mSpace), 0, SizeUtils.dp2px(view.getContext(), mSpace));
            } else {
                outRect.set(0, 0, 0, SizeUtils.dp2px(view.getContext(), mSpace));
            }
        } else {
            if (parent.getChildAdapterPosition(view) == 0) {
                outRect.set(SizeUtils.dp2px(view.getContext(), mSpace), 0, 0, 0);
            } else {
                outRect.set(SizeUtils.dp2px(view.getContext(), mSpace), 0, SizeUtils.dp2px(view.getContext(), mSpace), 0);
            }
        }
    }
}

이렇게하면 모든 항목의 위쪽과 아래쪽 (또는 왼쪽과 오른쪽)에 공간이 추가됩니다. 그러면 공간을로 설정할 수 있습니다 recyclerView.

recyclerView.addItemDecoration(new CommonItemSpaceDecoration(16));

SizeUtils.java

public class SizeUtils {
    public static int dp2px(Context context, float dpValue) {
        final float scale = context.getResources().getDisplayMetrics().density;
        return (int) (dpValue * scale + 0.5f);
    }
}
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.