PEMBARUAN 1
Sejak Android Support Library 23.2.0 ada metode tambahan setAutoMeasureEnabled(true)
untuk LayoutManagers. Itu membuat RecyclerView untuk membungkus konten itu dan bekerja seperti pesona.
http://android-developers.blogspot.ru/2016/02/android-support-library-232.html
Jadi tambahkan saja seperti ini:
LayoutManager layoutManager = new LinearLayoutManager(this);
layoutManager.setAutoMeasureEnabled(true);
recyclerView.setLayoutManager(layoutManager);
recyclerView.setNestedScrollingEnabled(false);
PEMBARUAN 2
Karena 27.1.0 setAutoMeasureEnabled
sudah tidak digunakan lagi, maka Anda harus menyediakan implementasi kustom LayoutManager dengan metode yang digantiisAutoMeasureEnabled()
Tetapi setelah banyak kasus penggunaan, RecyclerView saya sangat menyarankan untuk tidak menggunakannya mode pembungkus , karena ini bukan yang dimaksudkan untuk itu. Cobalah untuk memperbaiki seluruh tata letak Anda menggunakan RecyclerView tunggal normal dengan tipe beberapa item. Atau gunakan pendekatan dengan LinearLayout yang saya jelaskan di bawah ini sebagai pilihan terakhir
Jawaban lama (tidak disarankan)
Anda bisa menggunakannya RecyclerView
di dalam NestedScrollView
. Pertama-tama Anda harus menerapkan kebiasaan Anda sendiri LinearLayoutManager
, itu membuat Anda RecyclerView
untuk membungkus isinya. Sebagai contoh:
public class WrappingLinearLayoutManager extends LinearLayoutManager
{
public WrappingLinearLayoutManager(Context context) {
super(context);
}
private int[] mMeasuredDimension = new int[2];
@Override
public boolean canScrollVertically() {
return false;
}
@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++) {
if (getOrientation() == HORIZONTAL) {
measureScrapChild(recycler, i,
View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED),
heightSpec,
mMeasuredDimension);
width = width + mMeasuredDimension[0];
if (i == 0) {
height = mMeasuredDimension[1];
}
} else {
measureScrapChild(recycler, i,
widthSpec,
View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED),
mMeasuredDimension);
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) {
View view = recycler.getViewForPosition(position);
if (view.getVisibility() == View.GONE) {
measuredDimension[0] = 0;
measuredDimension[1] = 0;
return;
}
// For adding Item Decor Insets to view
super.measureChildWithMargins(view, 0, 0);
RecyclerView.LayoutParams p = (RecyclerView.LayoutParams) view.getLayoutParams();
int childWidthSpec = ViewGroup.getChildMeasureSpec(
widthSpec,
getPaddingLeft() + getPaddingRight() + getDecoratedLeft(view) + getDecoratedRight(view),
p.width);
int childHeightSpec = ViewGroup.getChildMeasureSpec(
heightSpec,
getPaddingTop() + getPaddingBottom() + getDecoratedTop(view) + getDecoratedBottom(view),
p.height);
view.measure(childWidthSpec, childHeightSpec);
// Get decorated measurements
measuredDimension[0] = getDecoratedMeasuredWidth(view) + p.leftMargin + p.rightMargin;
measuredDimension[1] = getDecoratedMeasuredHeight(view) + p.bottomMargin + p.topMargin;
recycler.recycleView(view);
}
}
Setelah itu gunakan ini LayoutManager
untuk AndaRecyclerView
recyclerView.setLayoutManager(new WrappingLinearLayoutManager(getContext()));
Tetapi Anda juga harus memanggil kedua metode itu:
recyclerView.setNestedScrollingEnabled(false);
recyclerView.setHasFixedSize(false);
Di sini setNestedScrollingEnabled(false)
nonaktifkan pengguliran RecyclerView
, sehingga tidak mencegat acara pengguliran NestedScrollView
. DansetHasFixedSize(false)
menentukan bahwa perubahan konten adaptor dapat mengubah ukuranRecyclerView
Catatan penting: Solusi ini sedikit bermasalah dalam beberapa kasus dan memiliki masalah dengan kinerja, jadi jika Anda memiliki banyak item dalam Anda, RecyclerView
saya akan merekomendasikan untuk menggunakan LinearLayout
implementasi berbasis tampilan daftar, buat analog Adaptor untuk itu dan buatlah berperilaku seperti ListView
atauRecyclerView