GridLayoutManager в упакованном макете не изменяет размер RecyclerView для отображения элементов
RecyclerView
с wrap_content
а также GridLayoutManager
не отображает элементы. Он не увеличивается, чтобы освободить место для предметов.
Прежде всего, я заметил, что есть проблема (74772), открытая для нее, но она еще не решена по состоянию на декабрь 2015 года, и не раньше "начала 2016 года".
Кто-то, кажется, сделал это CustomGridLayoutManager
также доступна на Github, но она все еще не дает достаточно места для всех предметов, делая RecyclerView
выглядят обрезанными (но прокручиваемыми), даже если для RecyclerView
в его родителя.
Любые идеи о том, как сделать RecyclerView
правильно оценивать элементы и показывать их без прокрутки, когда это возможно?
1 ответ
Этот класс, кажется, учитывает при измерении только первый дочерний элемент и первый дочерний элемент каждой строки (какой бы размер не был назначен, зависит от ориентации). Смотрите это (комментарии от меня):
if (getOrientation() == HORIZONTAL) {
if (i % getSpanCount() == 0) { // only for first child of row.
width = width + mMeasuredDimension[0];
}
if (i == 0) { // only for first item.
height = mMeasuredDimension[1];
}
}
Нечто подобное происходит с ориентацией VERTICAL
(пойман в else
что следует).
Чтобы учесть мои потребности, я измерил каждого ребенка, проверил самого большого ребенка в каждой строке, затем применил к строке максимальные ограничения. Когда каждая строка была закончена измерена, тогда размер строки был добавлен к необходимому общему размеру.
if (getOrientation() == VERTICAL) {
rowMeasure[1] = Math.max(rowMeasure[1], childMeasure[1]);
rowMeasure[0] += childMeasure[0];
} else {
rowMeasure[0] = Math.max(rowMeasure[0], childMeasure[0]);
rowMeasure[1] += childMeasure[1];
}
// When finishing the row (last item of row), adds the row dimensions to the view.
if (i % getSpanCount() == getSpanCount() - 1 || i == state.getItemCount() - 1) {
rowsSized[addIndex] += rowMeasure[addIndex];
rowsSized[maxIndex] = Math.max(rowsSized[maxIndex], rowMeasure[maxIndex]);
rowMeasure[addIndex] = 0;
rowMeasure[maxIndex] = 0;
}
Полный класс доступен в конце этого ответа. Выше показана только логика.
Я еще не полностью протестировал это решение, поскольку столкнулся с этой проблемой на этой неделе и попытался решить ее - опять же, по крайней мере, для моих нужд - вчера (декабрь 08).
Вы можете проверить, как я решил эту проблему с моим WrappedGridLayoutManager
здесь
Как указано в комментариях к проблеме, вы должны обратить внимание на RecyclerView
"s State
, используя его getItemCount()
вместо. Я также рекомендую взглянуть на getViewForPosition(int)
чтобы увидеть, если / как это может быть затронуто условиями предварительного просмотра и так далее.