나는이 DialogFragment
포함하는 RecyclerView
(카드 목록).
이 안에는 높이를 가질 수있는 RecyclerView
하나 이상 CardViews
이 있습니다.
안에 포함 된 DialogFragment
높이를 기준으로 올바른 높이를 지정 하고 싶습니다 CardViews
.
일반적으로 이것은 간단합니다. 나는 이와 같이 설정 wrap_content
했습니다 RecyclerView
.
<android.support.v7.widget.RecyclerView ...
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/recycler_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:clickable="true"
android:scrollbars="vertical" >
</android.support.v7.widget.RecyclerView>
나는 RecyclerView
이것을 사용하고 있기 때문에 작동하지 않는다.
https://issuetracker.google.com/issues/37001674
과
중첩 된 재활용 자보기 높이가 내용을 감싸지 않습니다.
이 두 페이지에서 사람들은 확장 LinearLayoutManager
하고 재정의 하도록 제안합니다onMeasure()
먼저 누군가가 첫 번째 링크에서 제공 한 LayoutManager 를 사용했습니다 .
public static class WrappingLayoutManager extends LinearLayoutManager {
public WrappingLayoutManager(Context context) {
super(context);
}
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);
measureScrapChild(recycler, 0,
View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED),
View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED),
mMeasuredDimension);
int width = mMeasuredDimension[0];
int height = mMeasuredDimension[1];
switch (widthMode) {
case View.MeasureSpec.EXACTLY:
case View.MeasureSpec.AT_MOST:
width = widthSize;
break;
case View.MeasureSpec.UNSPECIFIED:
}
switch (heightMode) {
case View.MeasureSpec.EXACTLY:
case View.MeasureSpec.AT_MOST:
height = heightSize;
break;
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 != 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();
measuredDimension[1] = view.getMeasuredHeight();
recycler.recycleView(view);
}
}
}
그러나 이 작동하지 않았다 때문에
heightSize = View.MeasureSpec.getSize(heightSpec);
관련이있는 것으로 보이는 매우 큰 값을 반환합니다. match_parent
.
height = heightSize;
(두 번째 스위치의 경우) 주석을 달아서 높이를 조절할 수 있었지만 TextView
내부의 자식 CardView
이 자체 텍스트 (긴 문장)를 감쌀 수없는 경우에만 가능합니다 .
TextView
그것이 감싸는 즉시 자체 텍스트 높이가 증가해야하지만 그렇지 않습니다. 긴 문장의 높이를 줄 바꿈이 아닌 한 줄로 계산했습니다 (2 개 이상).
나는이 개선 방법에 대한 조언 LayoutManager
그래서 내 RecyclerView
와 작품을 WRAP_CONTENT
?
편집 :이 레이아웃 관리자는 대부분의 사람들에게 효과적 일 수 있지만 여전히 텍스트 뷰 줄 바꿈의 스크롤 및 높이 계산에 문제가 있습니다.
public class MyLinearLayoutManager extends LinearLayoutManager {
public MyLinearLayoutManager(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) {
View view = recycler.getViewForPosition(position);
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);
}
}
}
Jan 22, 2016: This has been merged into the internal tree, should be available with the next version of support library.