У меня проблема с тем, что Jetpack compose отображает модель, содержащую ModelList
элементов. Когда добавляются новые элементы, порядок элементов пользовательского интерфейса становится неправильным.
Вот очень простой CounterModel
, содержащий ModelList
из ItemModel
s:
@Model
data class CounterModel(
var counter: Int = 0,
var name: String = "",
val items: ModelList<ItemModel> = ModelList()
)
@Model
data class ItemModel(
var name: String
)
На экране отображаются две строки карточек для каждого ItemModel
: RowA
и RowB
. Когда я создаю этот экран, инициализируется следующим CounterModel
:
val model = CounterModel()
model.name="hi"
model.items.add(ItemModel("Item 1"))
model.items.add(ItemModel("Item 2"))
CounterModelScreen(model)
... он отображается, как и ожидалось, вот так:
Позиция 1 Ряд A
Позиция 1 Ряд B
Позиция 2 Ряд A
Позиция 2 Ряд B
Когда я нажимаю кнопку "добавить" для вставки нового ItemModel
, я просто ожидаю увидеть
Позиция 3 Ряд A
Позиция 3 Ряд B
Внизу. Но вместо этого порядок беспорядочный, и я вижу две rowAs, а затем две rowB:
Позиция 1 Ряд A
Позиция 1 Ряд B
Позиция 2 Ряд A
Позиция 3 Ряд A
Позиция 3 Ряд B
Позиция 2 Ряд B
Я не очень понимаю, как это возможно. Код пользовательского интерфейса чрезвычайно прост: переберите items
и испустите RowA
и RowB
для каждого из них:
for (i in counterModel.items.indices) {
RowA(counterModel, i)
RowB(counterModel, i)
}
Использование Android Studio 4.0C6
Вот полный код:
@Composable
fun CounterModelScreen(counterModel: CounterModel) {
Column {
TopAppBar(title = {
Text(
text = "Counter Model"
)
})
CounterHeader(counterModel)
for (i in counterModel.items.indices) {
RowA(counterModel, i)
RowB(counterModel, i)
}
Button(
text = "Add",
onClick = {
counterModel.items.add(ItemModel("Item " + (counterModel.items.size + 1)))
})
}
}
@Composable
fun CounterHeader(counterModel: CounterModel) {
Text(text = counterModel.name)
}
@Composable
fun RowA(counterModel: CounterModel, index: Int) {
Padding(padding = 8.dp) {
Card(color = Color.White, shape = RoundedCornerShape(4.dp)) {
Column(crossAxisSize = LayoutSize.Expand) {
Text(
text = counterModel.items[index].name
)
Text(text = "Row A")
}
}
}
}
@Composable
fun RowB(counterModel: CounterModel, index: Int) {
Padding(padding = 8.dp) {
Card(color = Color.Gray, shape = RoundedCornerShape(4.dp)) {
Column(crossAxisSize = LayoutSize.Expand) {
Text(
text = counterModel.items[index].name
)
Text(text = "Row B")
}
}
}
}
CounterHeader(counterModel)
непосредственно над циклом for решает проблему, но это меня еще больше сбивает с толку.CounterHeader
Забава - это простоText(text = counterModel.name)
, почему это должно на что-то влиять? Это даже работает, если я встраиваюText
(т.е. убираю веселье). - person rockgecko   schedule 20.12.2019