Данные Recyclerview изменены без его указания - PullRequest
0 голосов
/ 11 июля 2020

Я выполняю некоторые операции в моем списке моделей, которые нужно передать адаптеру ресайклера, и обновляю список адаптеров. По какой-то неожиданной причине список адаптеров был обновлен до того, как я передал новый список. Я использую DiffUtil для вычисления разницы между oldList и newList.

internal fun CheckoutDetailsActivity.updateLineItemWithPartialPayment(lineItemModelToUpdate: LineItemModel){

    GlobalScope.launch {
        withContext(Dispatchers.Main) {
            calculateTodayPayments(lineItemModelToUpdate)
        }
    }
}

internal suspend fun  CheckoutDetailsActivity.calculateTodayPayments(lineItemModelToUpdate: LineItemModel){
    var todayPayments: BigDecimal = BigDecimal.ZERO
    val lineItems: ArrayList<LineItemModel> = ArrayList(viewModel.ticket?.lineItems)

    withContext(Dispatchers.Default){
        lineItems.forEachIndexed loop@{ index, lineItemModel ->
            if(lineItemModel.id == lineItemModelToUpdate.id){
                lineItems[index] = lineItemModelToUpdate
                todayPayments += lineItemModelToUpdate.partialPaymentAmount?: BigDecimal.ZERO
                return@loop
            }
            lineItemModel.inPartialPayment = true
            todayPayments += lineItemModel.partialPaymentAmount?: BigDecimal.ZERO
        }
    }

    viewModel.todayPayments = todayPayments

    updateRecyclerAdapter(lineItems)
    showTodayPaymentContainer()
}

internal fun CheckoutDetailsActivity.updateRecyclerAdapter(lineItems: ArrayList<LineItemModel>){
    viewModel.lineItemsWithPartialPayment.clear()
    viewModel.lineItemsWithPartialPayment.addAll(lineItems)
viewModel.recyclerViewAdapter?.submitList(viewModel.sortLineItems(ArrayList(lineItems)))
    viewModel.ticket?.lineItems = lineItems
}

это моя submitList () функция в адаптере:

 fun submitList(lineItemList: List<LineItemModel>){
        val oldLineItemList = lineItems
        val diffResult: DiffUtil.DiffResult = DiffUtil.calculateDiff(
            LineItemDiffCallback(
                oldLineItemList,
                lineItemList
            )
        )
        this.lineItems.clear()
        this.lineItems.addAll(lineItemList)
        diffResult.dispatchUpdatesTo(this)
    }

    class LineItemDiffCallback(
        var oldLineItemList: List<LineItemModel>,
        var newLineItemList: List<LineItemModel>
    ): DiffUtil.Callback(){
        override fun areItemsTheSame(oldItemPosition: Int, newItemPosition: Int): Boolean {
            return oldLineItemList[oldItemPosition].id == newLineItemList[newItemPosition].id
        }

        override fun getOldListSize(): Int {
           return oldLineItemList.size
        }

        override fun getNewListSize(): Int {
           return newLineItemList.size
        }

        override fun areContentsTheSame(oldItemPosition: Int, newItemPosition: Int): Boolean {
            return oldLineItemList[oldItemPosition] == newLineItemList[newItemPosition]
        }

    }

В последнем методе я обновляю список адаптеров с помощью submitList () , когда я проверяю список адаптеров в строке viewModel.todayPayments = todayPayments , он уже был обновлен с помощью предыдущей операции "forEachIndexed ()", по этой причине DiffUtil работает некорректно, поскольку не может найти разницу между oldList и newList .

1 Ответ

0 голосов
/ 11 июля 2020

updateLineItemWithPartialPayment вызывает calculateTodayPayments, который вызывает updateRecyclerAdapter, который вызывает updateLineItemWithPartialPayment, который вызывает calculateTodayPayments, который вызывает updateRecyclerAdapter [...] вы понимаете ...

Почему используются функции расширения? Разве вы не вызываете их из самого действия?

Другое дело ... эта submitList функция ваша или вы используете PagedListAdapter?

...