在MVVM中将DiffUtil中的notifyDataSetChanged与DiffUtil替换为数据绑定和LiveData

时间:2019-10-10 19:09:48

标签: android mvvm android-databinding android-livedata

使用MVVM,数据绑定,LiveData和notifyDataSetChanged()的TODO应用的google示例。我想用DiffUtil代替它。该示例将数据重新加载到片段的onResume函数中。

TasksFragment.java

在onResume函数中重新加载整个dataSet。

@Override
public void onResume() {
    super.onResume();
    mTasksViewModel.start();
}

tasks_frag.xml

<ListView
    android:id="@+id/tasks_list"
    app:items="@{viewmodel.items}"
    android:layout_width="match_parent"
    android:layout_height="wrap_content" />

Adapter

public class TasksAdapter extends BaseAdapter {
    private final TasksViewModel mTasksViewModel;
    private List<Task> mTasks;

    private void setList(List<Task> tasks) {
        mTasks = tasks;
        notifyDataSetChanged();
    }
}

TasksListBindings.java

public class TasksListBindings {

    @SuppressWarnings("unchecked")
    @BindingAdapter("app:items")
    public static void setItems(ListView listView, List<Task> items) {
        TasksAdapter adapter = (TasksAdapter) listView.getAdapter();
        if (adapter != null)
        {
            adapter.setData(items);
        }
    }
}

我已经实现了 DiffUtil 来代替 notifyDataSetChanged

protected void setList(List<Item> tasks) {
    Log.d("customeee", "mTasks setList");
    final ItemsDiffCallback diffCallback = new ItemsDiffCallback(this.mTasks, tasks);
    final DiffUtil.DiffResult diffResult = DiffUtil.calculateDiff(diffCallback);

    diffResult.dispatchUpdatesTo(this);
    this.mTasks.clear();
    this.mTasks.addAll(tasks);

}

但是无论我做什么,都会发生什么事 areContentsTheSame 函数始终返回true。如果我强求错误,则更新工作正常。

@Override
public boolean areContentsTheSame(int oldItemPosition, int newItemPosition) {
    final Item oldItem = mOldList.get(oldItemPosition);
    final Item newItem = mNewList.get(newItemPosition);

    Log.d("customeee", oldItem.getNote() + " newItem: "+newItem.getNote());
    Log.d("customeee", "New == old? "+mOldList.equals(mNewList));

    return oldItem.getNote().equals(newItem.getNote());
}

oldItem.getNote()和newItem.getNote()都返回新值。我认为如果列表对象为oldList.equals(newList),这与引用有关系。

1 个答案:

答案 0 :(得分:0)

解决方案:

Google提出了一个新的解决方案-AsyncListDiffer,而不是直接使用DiffUtil。来自类引用的This小代码示例带来了答案。

我还缺少一些东西。他们在Google sample中创建一个新对象,以保存到存储库中。需要哪个:

item = new Item(title.getValue(), description.getValue(), mTaskId, mItemCompleted);
updateItem(item);

我要做的只是用预期会更改的新值更新现有对象:

this.item.getValue().setFavorite(favorite.getValue());
this.item.getValue().setNote(note.getValue());
updateTask(item.getValue());

遵循AsyncListDifferGoogle sample app的实施指南有助于我解决此问题。