Asad
Asad

Reputation: 357

Set Height of Inner RecyclerView wrap_content

I have a recyclerview inside another recyclerview. I want to make height of inner recyclerview "warp_content".

I came to know it is possible with new version of recyclerview which is mentioned below.

'com.android.support:recyclerview-v7:23.2.0'

But the problem is, by setting height = wrap_content I can see only first item.

Any Help will be great.

Upvotes: 4

Views: 4083

Answers (2)

Sahar
Sahar

Reputation: 311

Setting recyclerview item works for me. Outer wrapper relative layout is added intentionally to address issue layout_height="wrap_content" does NOT occupy the height of all the elements added to it via adapter. The result is cut out items that is outside of device viewport when it loads initially. Wrapping "RecyclerView" with "RelativeLayout" fixes the issue on Marshmallow devices.

<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:descendantFocusability="blocksDescendants">

<android.support.v7.widget.RecyclerView
    android:id="@+id/rv_test"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    tools:listitem="@layout/test_item"></android.support.v7.widget.RecyclerView>
</RelativeLayout>

Upvotes: 2

Maheshwar Ligade
Maheshwar Ligade

Reputation: 6855

Because I am using a RecyclerView this does not work see:

https://code.google.com/p/android/issues/detail?id=74772

and

Nested Recycler view height doesn't wrap it's content

On both of these pages people suggest to extend LinearLayoutManager and to override onMeasure()

RecyclerView doesn't have the wrap_content by default. You have to use the RecyclerView with wrap_content Layout Manager such as, WrapLinearLayoutManager e.g CustomLinearLayoutManager .

CustomLinearLayoutManager.java

    public class CustomLinearLayoutManager extends LinearLayoutManager {

private static final String TAG = CustomLinearLayoutManager.class.getSimpleName();

public CustomLinearLayoutManager(Context context) {
    super(context);
}

public CustomLinearLayoutManager(Context context, int orientation, boolean reverseLayout) {
    super(context, orientation, reverseLayout);
}

private int[] mMeasuredDimension = new int[2];

@Override
public void onMeasure(RecyclerView.Recycler recycler, RecyclerView.State state, int widthSpec, int heightSpec) {

    final int widthMode = View.MeasureSpec.getMode(widthSpec);
    final int heightMode = View.MeasureSpec.getMode(heightSpec);
    final int widthSize = View.MeasureSpec.getSize(widthSpec);
    final int heightSize = View.MeasureSpec.getSize(heightSpec);

    int width = 0;
    int height = 0;
    for (int i = 0; i < getItemCount(); i++) {
        measureScrapChild(recycler, i, View.MeasureSpec.makeMeasureSpec(i, View.MeasureSpec.UNSPECIFIED),
            View.MeasureSpec.makeMeasureSpec(i, View.MeasureSpec.UNSPECIFIED),
            mMeasuredDimension);


        if (getOrientation() == HORIZONTAL) {
            width = width + mMeasuredDimension[0];
            if (i == 0) {
                height = mMeasuredDimension[1];
            }
        } else {
            height = height + mMeasuredDimension[1];
            if (i == 0) {
                width = mMeasuredDimension[0];
            }
        }
    }
    switch (widthMode) {
        case View.MeasureSpec.EXACTLY:
            width = widthSize;
        case View.MeasureSpec.AT_MOST:
        case View.MeasureSpec.UNSPECIFIED:
    }

    switch (heightMode) {
        case View.MeasureSpec.EXACTLY:
            height = heightSize;
        case View.MeasureSpec.AT_MOST:
        case View.MeasureSpec.UNSPECIFIED:
    }

    setMeasuredDimension(width, height);
}

private void measureScrapChild(RecyclerView.Recycler recycler, int position, int widthSpec,
                           int heightSpec, int[] measuredDimension) {
    try {
        View view = recycler.getViewForPosition(0);//fix 动态添加时报IndexOutOfBoundsException

        if (view != null) {
            RecyclerView.LayoutParams p = (RecyclerView.LayoutParams) view.getLayoutParams();

            int childWidthSpec = ViewGroup.getChildMeasureSpec(widthSpec,
                getPaddingLeft() + getPaddingRight(), p.width);

            int childHeightSpec = ViewGroup.getChildMeasureSpec(heightSpec,
                getPaddingTop() + getPaddingBottom(), p.height);

            view.measure(childWidthSpec, childHeightSpec);
            measuredDimension[0] = view.getMeasuredWidth() + p.leftMargin + p.rightMargin;
            measuredDimension[1] = view.getMeasuredHeight() + p.bottomMargin + p.topMargin;
            recycler.recycleView(view);
        }
    } catch (Exception e) {
        e.printStackTrace();
    } 
}

}

Upvotes: 8

Related Questions