第八章:Paging增刪改查功能實現

  • 效果

在這裏插入圖片描述

  • MutableItemKeyedDataSource 管理數據源

/**
 * 一個可變更的ItemKeyedDataSource 數據源
 * <p>
 * 工作原理是:我們知道DataSource是會被PagedList 持有的。
 * 一旦,我們調用了new PagedList.Builder<Key, Value>().build(); 那麼就會立刻觸發當前DataSource的loadInitial()方法,而且是同步
 * 詳情見ContiguousPagedList的構造函數,而我們在當前DataSource的loadInitial()方法中返回了 最新的數據集合 data。
 * 一旦,我們再次調用PagedListAdapter#submitList()方法 就會觸發差分異計算 把新數據變更到列表之上了。
 *
 * @param <Key>
 * @param <Value>
 */
@SuppressLint("RestrictedApi")
public abstract class MutableItemKeyedDataSource<Key, Value> extends ItemKeyedDataSource<Key, Value> {
    private ItemKeyedDataSource mDataSource;

    public List<Value> data = new ArrayList<>();

    public PagedList<Value> buildNewPagedList(PagedList.Config config) {
         PagedList<Value> pagedList = new PagedList.Builder<Key, Value>(this, config)
                .setFetchExecutor(ArchTaskExecutor.getIOThreadExecutor())
                .setNotifyExecutor(ArchTaskExecutor.getMainThreadExecutor())
                .build();

        return pagedList;
    }

    public MutableItemKeyedDataSource(ItemKeyedDataSource dataSource) {

        mDataSource = dataSource;
    }

    @Override
    public void loadInitial(@NonNull LoadInitialParams<Key> params, @NonNull LoadInitialCallback<Value> callback) {
        callback.onResult(data);
    }

    @Override
    public void loadAfter(@NonNull LoadParams<Key> params, @NonNull LoadCallback<Value> callback) {
        if (mDataSource != null) {
            //一旦 和當前DataSource關聯的PagedList被提交到PagedListAdapter。那麼ViewModel中創建的DataSource 就不會再被調用了
            //我們需要在分頁的時候 代理一下 原來的DataSource,迫使其繼續工作
            mDataSource.loadAfter(params, callback);
        }
    }

    @Override
    public void loadBefore(@NonNull LoadParams<Key> params, @NonNull LoadCallback<Value> callback) {
        callback.onResult(Collections.emptyList());
    }

    @NonNull
    @Override
    public abstract Key getKey(@NonNull Value item);
}

  • 增加數據
 //增加數據
    public void addAndRefreshList(Teacher.RecordsBean item) {
        PagedList<Teacher.RecordsBean> currentList = getCurrentList();
        MutableItemKeyedDataSource<String, Teacher.RecordsBean> dataSource =
                new MutableItemKeyedDataSource<String, Teacher.RecordsBean>((ItemKeyedDataSource) currentList.getDataSource()) {
                    @NonNull
                    @Override
                    public String getKey(@NonNull Teacher.RecordsBean item) {
                        return item.getPaintingId();
                    }
                };
        dataSource.data.add(item);
        dataSource.data.addAll(currentList.snapshot());
        PagedList<Teacher.RecordsBean> pagedList = dataSource.buildNewPagedList(currentList.getConfig());
        submitList(pagedList, new Runnable() {
            @Override
            public void run() {
                notifyDataSetChanged();
            }
        });
    }
  • 刪除數據

    //刪除數據
    public void deleteAndRefreshList(Teacher.RecordsBean item) {
        PagedList<Teacher.RecordsBean> currentList = getCurrentList();
        MutableItemKeyedDataSource<String, Teacher.RecordsBean> dataSource =
                new MutableItemKeyedDataSource<String, Teacher.RecordsBean>((ItemKeyedDataSource) currentList.getDataSource()) {
                    @NonNull
                    @Override
                    public String getKey(@NonNull Teacher.RecordsBean item) {
                        return item.getPaintingId();
                    }
                };
        for (Teacher.RecordsBean recordsBean : currentList.snapshot()) {
            if (recordsBean != item) {
                dataSource.data.add(recordsBean);
            }
        }
        PagedList<Teacher.RecordsBean> pagedList = dataSource.buildNewPagedList(currentList.getConfig());
        submitList(pagedList, new Runnable() {
            @Override
            public void run() {
                notifyDataSetChanged();
            }
        });
    }

  • 修改數據

    //修改數據
    public void upDateAndRefreshList(Teacher.RecordsBean item) {
        PagedList<Teacher.RecordsBean> currentList = getCurrentList();
        MutableItemKeyedDataSource<String, Teacher.RecordsBean> dataSource =
                new MutableItemKeyedDataSource<String, Teacher.RecordsBean>((ItemKeyedDataSource) currentList.getDataSource()) {
                    @NonNull
                    @Override
                    public String getKey(@NonNull Teacher.RecordsBean item) {
                        return item.getPaintingId();
                    }
                };
        for (Teacher.RecordsBean recordsBean : currentList.snapshot()) {
            if (recordsBean == item) {
                recordsBean.setPaintingName("我是修改的:" + recordsBean.getPaintingName());
            }
        }
        dataSource.data.addAll(currentList);
        PagedList<Teacher.RecordsBean> pagedList = dataSource.buildNewPagedList(currentList.getConfig());
        submitList(pagedList, new Runnable() {
            @Override
            public void run() {
                notifyDataSetChanged();
            }
        });
    }
  • 查詢數據
 List<Teacher.RecordsBean> lists = adapter.getCurrentList().snapshot();
                        for (Teacher.RecordsBean list : lists) {
                            Log.e("TTT", list.getPaintingId()+""+list.getPaintingName());

                        }

詳細代碼
  • AddDeleteAdapter

public class AddDeleteAdapter extends PagedListAdapter<Teacher.RecordsBean, AddDeleteAdapter.ViewHolder> {
    protected Context mContext;
    private AddDeleteCallback mCallback;

    public AddDeleteAdapter(Context context, AddDeleteCallback callback) {
        super(new DiffUtil.ItemCallback<Teacher.RecordsBean>() {
            @Override
            public boolean areItemsTheSame(@NonNull Teacher.RecordsBean oldItem, @NonNull Teacher.RecordsBean newItem) {
                //判斷item是否相等(這裏根據id來判斷)
                return oldItem.getPaintingId() == newItem.getPaintingId();
            }

            @Override
            public boolean areContentsTheSame(@NonNull Teacher.RecordsBean oldItem, @NonNull Teacher.RecordsBean newItem) {
                //判斷內容是否相等(重寫equals方法)
                return oldItem.equals(newItem);
            }
        });
        this.mContext = context;
        this.mCallback = callback;
    }

    @NonNull
    @Override
    public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        LayoutTeacherTypeBinding binding = LayoutTeacherTypeBinding.inflate(LayoutInflater.from(mContext), parent, false);
        return new ViewHolder(binding.getRoot(), binding);
    }

    @Override
    public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
        holder.binData(getItem(position));
        holder.itemView.setOnClickListener(v -> {
            mCallback.clickItem(position, getItem(position));
        });
    }


    public class ViewHolder extends RecyclerView.ViewHolder {
        private LayoutTeacherTypeBinding mBinding;

        public ViewHolder(@NonNull View itemView, LayoutTeacherTypeBinding binding) {
            super(itemView);
            this.mBinding = binding;
        }

        public void binData(Teacher.RecordsBean item) {
            mBinding.setItem(item);
        }
    }

    //增加數據
    public void addAndRefreshList(Teacher.RecordsBean item) {
        PagedList<Teacher.RecordsBean> currentList = getCurrentList();
        MutableItemKeyedDataSource<String, Teacher.RecordsBean> dataSource =
                new MutableItemKeyedDataSource<String, Teacher.RecordsBean>((ItemKeyedDataSource) currentList.getDataSource()) {
                    @NonNull
                    @Override
                    public String getKey(@NonNull Teacher.RecordsBean item) {
                        return item.getPaintingId();
                    }
                };
        dataSource.data.add(item);
        dataSource.data.addAll(currentList.snapshot());
        PagedList<Teacher.RecordsBean> pagedList = dataSource.buildNewPagedList(currentList.getConfig());
        submitList(pagedList, new Runnable() {
            @Override
            public void run() {
                notifyDataSetChanged();
            }
        });
    }

    //刪除數據
    public void deleteAndRefreshList(Teacher.RecordsBean item) {
        PagedList<Teacher.RecordsBean> currentList = getCurrentList();
        MutableItemKeyedDataSource<String, Teacher.RecordsBean> dataSource =
                new MutableItemKeyedDataSource<String, Teacher.RecordsBean>((ItemKeyedDataSource) currentList.getDataSource()) {
                    @NonNull
                    @Override
                    public String getKey(@NonNull Teacher.RecordsBean item) {
                        return item.getPaintingId();
                    }
                };
        for (Teacher.RecordsBean recordsBean : currentList.snapshot()) {
            if (recordsBean != item) {
                dataSource.data.add(recordsBean);
            }
        }
        PagedList<Teacher.RecordsBean> pagedList = dataSource.buildNewPagedList(currentList.getConfig());
        submitList(pagedList, new Runnable() {
            @Override
            public void run() {
                notifyDataSetChanged();
            }
        });
    }

    //修改數據
    public void upDateAndRefreshList(Teacher.RecordsBean item) {
        PagedList<Teacher.RecordsBean> currentList = getCurrentList();
        MutableItemKeyedDataSource<String, Teacher.RecordsBean> dataSource =
                new MutableItemKeyedDataSource<String, Teacher.RecordsBean>((ItemKeyedDataSource) currentList.getDataSource()) {
                    @NonNull
                    @Override
                    public String getKey(@NonNull Teacher.RecordsBean item) {
                        return item.getPaintingId();
                    }
                };
        for (Teacher.RecordsBean recordsBean : currentList.snapshot()) {
            if (recordsBean == item) {
                recordsBean.setPaintingName("我是修改的:" + recordsBean.getPaintingName());
            }
        }
        dataSource.data.addAll(currentList);
        PagedList<Teacher.RecordsBean> pagedList = dataSource.buildNewPagedList(currentList.getConfig());
        submitList(pagedList, new Runnable() {
            @Override
            public void run() {
                notifyDataSetChanged();
            }
        });
    }
}

  • AddAndDeleteFragment

public class AddAndDeleteFragment extends AbsListFragment<Teacher.RecordsBean, AddDeleteViewModel> implements AddDeleteCallback {


    private AlertDialog dialog;
    private AddDeleteAdapter mAdapter;

    public static AddAndDeleteFragment newInstance() {
        return new AddAndDeleteFragment();
    }

    @Override
    public void onDestroyView() {
        super.onDestroyView();
        dialog.dismiss();
    }

    @Override
    protected void onCreateViewFrame(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        mRefreshLayout.setEnableLoadMore(false);
    }

    @Override
    public PagedListAdapter getAdapter() {
        mAdapter = new AddDeleteAdapter(mContext, this);
        return mAdapter;
    }

    /**
     * paging只要有一次返回味空,就停止分頁了,要手動處理
     *
     * @param refreshLayout
     */
    @Override
    public void onLoadMore(@NonNull RefreshLayout refreshLayout) {

    }

    @Override
    public void onRefresh(@NonNull RefreshLayout refreshLayout) {
        //invalidate 之後Paging會重新創建一個DataSource 重新調用它的loadInitial方法加載初始化數據
        //詳情見:LivePagedListBuilder#compute方法
        mViewModel.getDataSource().invalidate();
    }

    private int index = 0;

    @Override
    public void clickItem(int position, Teacher.RecordsBean item) {
        Log.e("TTT", "position==>" + position);
        dialog = new AlertDialog.Builder(mContext)
                .setContentView(R.layout.layout_dialog)
                .setTitle(R.id.tv_title, item.getPaintingName())
                .setOnClicklistener(R.id.btn_add, new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        dialog.dismiss();
                        index++;
                        //增加數據
                        Teacher.RecordsBean recordsBean = new Teacher.RecordsBean();
                        recordsBean.setPaintingId(item.getPaintingId() + index);
                        recordsBean.setPaintingName("我是新增加的數據");
                        mAdapter.addAndRefreshList(recordsBean);
                    }
                })
                .setOnClicklistener(R.id.btn_delete, new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        dialog.dismiss();
                        //刪除數據
                        mAdapter.deleteAndRefreshList(item);
                    }
                })
                .setOnClicklistener(R.id.btn_update, new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        dialog.dismiss();
                        //修改數據
                        mAdapter.upDateAndRefreshList(item);
                    }
                })
                .setOnClicklistener(R.id.btn_query, new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        dialog.dismiss();
                        List<Teacher.RecordsBean> lists = adapter.getCurrentList().snapshot();
                        for (Teacher.RecordsBean list : lists) {
                            Log.e("TTT", list.getPaintingId()+""+list.getPaintingName());

                        }
                    }
                })
                .addDefaultAnimation()
                .setCancelable(true)
                .fullWidth()
                .show();
    }
}

demo地址:https://gitee.com/huangxiaoguo/jetpackandrxjava

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章