Jetpack插件化学习之AndroidX Paging 大数据列表加载库一

Jetpack插件化学习之AndroidX Paging 大数据列表加载库<一>

本文根据以下思路进行Paging的学习:

  1. Paging介绍
  2. Paing核心组件
  3. 总结梳理

Paging介绍

分页库使您可以更轻松地在应用程序中逐步和优雅地加载数据 RecyclerView。

许多应用程序使用包含大量项目的数据源中的数据,但一次只显示一小部分。

分页库可帮助您的应用观察并显示此数据的合理子集。此功能有几个优点:

  1. 数据请求消耗的网络带宽更少,系统资源更少。拥有计量或小数据计划的用户会欣赏这些具有数据意识的应用程序。
  2. 即使在数据更新和刷新期间,应用程序仍会继续快速响应用户输入。

来源自官方翻译

简单点说,
Paging给开发者提供了更为便捷的RecycleView数据加载方式。

  1. 便捷的分页加载方式,应用内存压力小网络压力更小(分成几次加载,肯定比一次加载好,现有模式就是这样)
  2. 用户体验好,无感数据加载,形成信息流。激发用户探索欲望。(这也是我们为什么选择他的一部分原因),嗯,确实逐步并优雅。

Paing核心组件

  1. DataSource:数据的来源
  2. PageList:配置取数据方式
  3. LivePagedListBuilder:构建取数据的机器

下图表示Paging工作中数据的流向。

注:想一下水泵抽水过程。螺旋桨吸水、滤网过滤、组建水泵。

image

同时,Paging把大部分的工作都放在了子线程做,UI线程只负责数据的显示。

DataSource

获取数据的类,Paging提供了三种不同的分页方式:PageKeyedDataSourcePositionalDataSourceItemKeyedDataSource

PageKeyedDataSource

通常使用在论坛,贴吧中。根据传入的页面num进行获取某一页的数据,比如获取第10页。

PositionalDataSource

Android开发中经常使用的分页,例如,每页10条,默认显示第一页。 CONTENT_LENGTH=10、mPage=1。

ItemKeyedDataSource

使用上一条data对象里某一个值作为下一页请求的关键字。这种情况多出现在服务端已经完成了分页效果,在某一个对象添加如“下一页”这样的标识数据。

上述组件根据业务逻辑不通使用不同类型。常用的为PositionalDataSource

使用以上之一的数据加载源需要跟下一个组件进行组合配置使用。

PageList

PageList提供了一系列的配置接口,方便开发者便捷的应付变幻莫测的需求。

使用PagedList.Config 提供的接口进行配置。
image

 /**
         * When {@link #maxSize} is set to {@code MAX_SIZE_UNBOUNDED}, the maximum number of items
         * loaded is unbounded, and pages will never be dropped.
         */
         // MAX_SIZE=MAX_SIZE_UNBOUNDED的情况,数据会一直加载
        @SuppressWarnings("WeakerAccess")
        public static final int MAX_SIZE_UNBOUNDED = Integer.MAX_VALUE;

        /**
         * Size of each page loaded by the PagedList.
         */
         // 每个界面加载数据的长度 CONTENT_LENGTH
        public final int pageSize;

        /**
         * Prefetch distance which defines how far ahead to load.
         * <p>
         * If this value is set to 50, the paged list will attempt to load 50 items in advance of
         * data that's already been accessed.
         *
         * @see PagedList#loadAround(int)
         */
         // 预加载 数据长度。 设置为50,当你看到第一个数据时候,第50条数据已加载完成
        @SuppressWarnings("WeakerAccess")
        public final int prefetchDistance;

        /**
         * Defines whether the PagedList may display null placeholders, if the DataSource provides
         * them.
         */
         // 数据没有加载成功时候,底部的占位符,相当于"加载更过"
        @SuppressWarnings("WeakerAccess")
        public final boolean enablePlaceholders;

        /**
         * Defines the maximum number of items that may be loaded into this pagedList before pages
         * should be dropped.
         * <p>
         * {@link PageKeyedDataSource} does not currently support dropping pages - when
         * loading from a {@code PageKeyedDataSource}, this value is ignored.
         *
         * @see #MAX_SIZE_UNBOUNDED
         * @see Builder#setMaxSize(int)
         */
         // 最大加载量,数据加载到最大量之后,将会删除
        public final int maxSize;

        /**
         * Size hint for initial load of PagedList, often larger than a regular page.
         */
         // 一个提示大小
        @SuppressWarnings("WeakerAccess")
        public final int initialLoadSizeHint;

上述的配置已经满足我们基本需求,根据不同的场景设置不同的pageSize,达到更好的用户体验。

LivePagedListBuilder

上面我们已经讲过了两个组件,分别是DataSource(螺旋桨)、PagedList(过滤网)。

接下来我们就要把这些组装起来,完成build过程。
该组件提供构造函数满足我们组件的需求,

   mLiveData = new LivePagedListBuilder(new PageDataSourceFactory(positionalDataSource)
                , new PagedList.Config.Builder().setPageSize(CONTENT_LENGTH)
                .setPrefetchDistance(CONTENT_LENGTH)
                .setEnablePlaceholders(false).setInitialLoadSizeHint(CONTENT_LENGTH)
                .build()).build();

可以看到,通过该类的构造函数,将DataSource与PagedList绑定在一起,完成build.

那这个Builder返回的对象是一个什么样的类型呢???

LiveData<PagedList<GankData>> mLiveData

分页库实现了应用程序体系结构指南中建议的观察者模式 。特别是,库的核心组件创建LiveDataUI可以观察的实例 (或等效的基于RxJava2的类)。然后,您的应用程序的UI可以PagedList在生成对象时显示对象中的内容 ,同时尊重UI控制器的 生命周期。

返回的是一个LiveData类型的对象。他负责把获取的数据发送给到主线程。(水泵口接上了水管)。

:还有一个需要注意的是RecycleView的adapter需要继承Paging自定义的PageAdapter。


public class MyAdapter extends PagedListAdapter<GankData, BaseViewHolder> {
    private Context mContext;

    protected MyAdapter(@NonNull DiffUtil.ItemCallback<GankData> diffCallback) {
        super(diffCallback);
    }


    @NonNull
    @Override
    public BaseViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        mContext = parent.getContext();
        return new BaseViewHolder(LayoutInflater.from(mContext).inflate(R.layout.item_main, parent, false));
    }

    @Override
    public void onBindViewHolder(@NonNull BaseViewHolder holder, int position) {
        TextView tvName = holder.getView(R.id.tv_name);
        ImageView imageView = holder.getView(R.id.iv);

        GankData data = getItem(position);
        tvName.setText(position+"");
         GlideUtils.loadImage(mContext,imageView,data.getUrl());

    }
}

总结

优点:Paging使得分页变得逻辑清晰、高效、便捷、优雅。同时又提升了用户体验。被分页问题搞到的同学可以尝试使用Paging作为解决方案。

缺点:配置相对繁琐,不同的界面界面的代码相对增加,初次使用比较麻烦(再加上AndroidX的刺激问题)

好了,Paging的初识至此告一段落,下一步我们来上手使用,感受以下它的魅力。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值