Android 資訊類App項(xiàng)目實(shí)戰(zhàn) 第六章 加載更多

前言:

正在做一個(gè)資訊類app,打算一邊做一邊整理,供自己學(xué)習(xí)與鞏固哩盲。用到的知識(shí)復(fù)雜度不高前方,僅適于新手。經(jīng)驗(yàn)不多廉油,如果寫(xiě)出來(lái)的代碼有不好的地方歡迎討論惠险。

以往的內(nèi)容

第一章 滑動(dòng)頂部導(dǎo)航欄

第二章 retrofit獲取網(wǎng)絡(luò)數(shù)據(jù)

第三章 新聞模塊

第四章 電影模塊

第五章 視頻模塊

第六章 加載更多

本章內(nèi)容最終效果:

加載更多效果.gif

加載更多效果3.gif

知識(shí)點(diǎn):

RecyclerView.ViewHolder

學(xué)習(xí)目標(biāo):

1、使用RecyclerView的適配器Adapter來(lái)加載不同布局抒线。

2班巩、使用RecyclerView的OnScrollListener來(lái)判斷列表狀態(tài)。

前五章的數(shù)據(jù)展示內(nèi)容是有限的嘶炭,滑到底部后就不再加載抱慌,本章內(nèi)容將完成新聞模塊用戶上滑到底部加載更多的功能,其它模塊上滑解決思路與新聞模塊相同眨猎,交由章節(jié)任務(wù)里完成抑进,本章不重復(fù)講解。

項(xiàng)目實(shí)戰(zhàn):

注意

本章用到的drawable資源睡陪、values資源皆存放在百度網(wǎng)盤(pán)

(請(qǐng)將values文件夾中的style.xml或color.xml更新一致后再運(yùn)行寺渗,如有后續(xù)更新自行修改)

1.1用到的Api:

新聞模塊:

http://c.m.163.com/nc/article/headline/T1348647909107/20-20.html

新聞模塊在startPage的地方設(shè)置為20或以上的數(shù)字,返回的數(shù)據(jù)就能達(dá)到加載更多的效果兰迫。

image.png
電影模塊:

https://api.douban.com/v2/movie/in_theaters?start=20
電影模塊需要添加應(yīng)該參數(shù)start户秤,這是在前面的電影模塊里沒(méi)有的。

image.png

視頻模塊:

視頻模塊的數(shù)據(jù)只要加載一次就會(huì)刷新一次逮矛,所以需要加載更多的時(shí)候正常加載就好了。

1.2 正在加載狀態(tài)顯示

上滑加載更多有很多種寫(xiě)法转砖,這里我們用的是在適配器改變RecyclerView的ViewHolder的方法须鼎。
首先我們新建一個(gè)布局文件,命名為footer.xml

footer.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="horizontal"
android:id="@+id/ll_footer">
<ProgressBar
    android:layout_width="40dp"
    android:layout_height="wrap_content"
    android:padding="5dp"
    android:id="@+id/pb_footer"
    style="@style/common_mProgress_circle"
    />
<TextView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:textSize="20sp"
    android:layout_margin="15dp"
    android:gravity="center"
    android:text="正在加載......"/>
</LinearLayout>

接下來(lái)是最麻煩的Adapter代碼了府蔗。

在ItemNewsAdapter中晋控,我們onCreateViewHolder直接寫(xiě)死返回ItemNewsHolder,這種做法不夠靈活姓赤。

修改前

我們需要將它修改成RecyclerView.ViewHolder

image.png

單是這樣還不夠赡译,我們還要在onBindViewHolder中判斷此時(shí)用的是哪個(gè)ViewHolder。

image.png

上面所做的一切不铆,都是為了能讓RecyclerView加載不同的布局蝌焚。
我們來(lái)寫(xiě)一個(gè)Footer的ViewHolder裹唆。


image.png

然后我們需要在列表拉倒底部時(shí)顯示它,是否拉到底部我們用自定義ViewType來(lái)判斷只洒。

重寫(xiě)getItemViewType方法

image.png

然后在onCreateViewHolder中加上判斷

image.png

ItemNewsAdapter的代碼:

public class ItemNewsAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {

private List<NewsBean.Bean> objects = new ArrayList<NewsBean.Bean>();

private Context context;

public ItemNewsAdapter(Context context) {
    this.context = context;
}

public void setData(List<NewsBean.Bean> objects) {
    this.objects = objects;
}

@Override
public int getItemViewType(int position) {
    if (position + 1 == getItemCount()) {
        return 1;
    } else {
        return 0;
    }
}

@Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    if (viewType == 0) {
        View view = LayoutInflater.from(parent.getContext())
                .inflate(R.layout.item_news, parent, false);
        return new ItemNewsHolder(view);
    } else {
        View view = LayoutInflater.from(parent.getContext())
                .inflate(R.layout.footer, parent, false);
        return new FooterHolder(view);
    }

}

@Override
public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
    if (holder instanceof ItemNewsHolder) {
        final NewsBean.Bean bean = objects.get(position);
        if (bean == null) {
            return;
        }
        Glide.with(context)
                .load(bean.getImgsrc())
                .into(((ItemNewsHolder) holder).ivNewsImg);
        if (position == 0) {
            ((ItemNewsHolder) holder).tvNewsDigest.setVisibility(View.GONE);
            ((ItemNewsHolder) holder).tvNewsTitle.setText("圖片:" + bean.getTitle());
        } else {
            ((ItemNewsHolder) holder).tvNewsTitle.setText(bean.getTitle());
            ((ItemNewsHolder) holder).tvNewsDigest.setText(bean.getMtime() + " : " + bean.getDigest());
            ((ItemNewsHolder) holder).cvNews.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    Intent intent = new Intent(context, ADetailActivity.class);
                    intent.putExtra("url", bean.getUrl());
                    intent.putExtra("title", bean.getTitle());
                    context.startActivity(intent);
                }
            });
        }
    }
}


@Override
public long getItemId(int position) {
    return position;
}

@Override
public int getItemCount() {
    return objects.size();
}

protected class ItemNewsHolder extends RecyclerView.ViewHolder {
    private ImageView ivNewsImg;
    private TextView tvNewsTitle;
    private TextView tvNewsDigest;
    private CardView cvNews;

    public ItemNewsHolder(View view) {
        super(view);
        ivNewsImg = (ImageView) view.findViewById(R.id.iv_news_img);
        tvNewsTitle = (TextView) view.findViewById(R.id.tv_news_title);
        tvNewsDigest = (TextView) view.findViewById(R.id.tv_news_digest);
        cvNews = (CardView) view.findViewById(R.id.cv_news);
    }
}

protected class FooterHolder extends RecyclerView.ViewHolder {

    public FooterHolder(View itemView) {
        super(itemView);
    }
}
}
效果:
正在加載.gif

1.3 Fragment

我們需要一個(gè)layoutManager來(lái)給我們判斷列表是否達(dá)到底部许帐,還有startPage來(lái)作為加載更多的參數(shù)。

image.png

然后修改設(shè)置RecyclerView部分的代碼毕谴。


image.png

寫(xiě)一個(gè)loadMore的方法成畦,當(dāng)執(zhí)行時(shí)startPage+20:

image.png

再給RecyclerView加上addOnScrollListener的設(shè)置。

image.png

2.1 Model層

上面的操作只是完成了頁(yè)面對(duì)列表狀態(tài)的判斷涝开,相對(duì)的循帐,數(shù)據(jù)獲取層也需要添加一些方法對(duì)數(shù)據(jù)返回做回應(yīng)。

Model層需要添加一個(gè)監(jiān)聽(tīng)加載更多的方法:

INewsLoadListener.java

NewsModel對(duì)startPage的不同對(duì)應(yīng)調(diào)用監(jiān)聽(tīng)的方法也不同:

NewsModel.java

2.2 View層

View層需要添加一個(gè)顯示更多數(shù)據(jù)的方法:

INewsView.java

2.3 Presenter層

Presenter層得補(bǔ)上剛剛Model層寫(xiě)的loadMoreSuccess方法:

NewsPresenter.java

在加載更多的時(shí)候舀武,上面SwipeRefreshLayout的圓形加載框就不要出現(xiàn)了拄养,寫(xiě)一個(gè)判斷區(qū)別它。

NewsPresenter.java

3.1 數(shù)據(jù)添加

我們獲取到加載更多的數(shù)據(jù)后奕剃,需要將它添加到recyclerView列表中衷旅,所以我們?cè)貯dapter中加上添加數(shù)據(jù)的方法:

ItemNewsAdapter.java

做完上面步驟后,我們回到FgNewsListFragment纵朋,把View層添加的showMoreNews方法補(bǔ)上:

FgNewsListFragment.java

在加載更多狀態(tài)下柿顶,網(wǎng)絡(luò)請(qǐng)求出錯(cuò)時(shí),最好把正在加載的布局關(guān)掉操软,所以在showErrorMsg方法中嘁锯,我們加上RecyclerView移除布局的代碼:

FgNewsListFragment.java

最終效果:

加載更多效果.gif

出現(xiàn)錯(cuò)誤時(shí)的效果:


加載更多效果2.gif

學(xué)習(xí)任務(wù)

把電影模塊的加載更多、視頻模塊的加載更多也做出來(lái)聂薪。

電影模塊效果:
只做了正在熱映的加載更多家乘,需要注意的是:

正在熱映start超過(guò)40的時(shí)候返回的數(shù)據(jù)是空的,需要給用戶作出判斷并且提示“沒(méi)有更多了”藏澳。
加載更多效果3.gif

視頻模塊效果:

加載更多效果4.gif

項(xiàng)目源碼:https://github.com/Huigesi/IdleReaderDemo

上一章:
第五章 視頻模塊

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末仁锯,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子翔悠,更是在濱河造成了極大的恐慌业崖,老刑警劉巖,帶你破解...
    沈念sama閱讀 217,907評(píng)論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件蓄愁,死亡現(xiàn)場(chǎng)離奇詭異双炕,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)撮抓,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,987評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門(mén)妇斤,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人,你說(shuō)我怎么就攤上這事站超≥┧。” “怎么了?”我有些...
    開(kāi)封第一講書(shū)人閱讀 164,298評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵顷编,是天一觀的道長(zhǎng)戚炫。 經(jīng)常有香客問(wèn)我,道長(zhǎng)媳纬,這世上最難降的妖魔是什么双肤? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,586評(píng)論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮钮惠,結(jié)果婚禮上茅糜,老公的妹妹穿的比我還像新娘。我一直安慰自己素挽,他們只是感情好蔑赘,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,633評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著预明,像睡著了一般缩赛。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上撰糠,一...
    開(kāi)封第一講書(shū)人閱讀 51,488評(píng)論 1 302
  • 那天酥馍,我揣著相機(jī)與錄音,去河邊找鬼阅酪。 笑死旨袒,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的术辐。 我是一名探鬼主播砚尽,決...
    沈念sama閱讀 40,275評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼辉词!你這毒婦竟也來(lái)了必孤?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 39,176評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤瑞躺,失蹤者是張志新(化名)和其女友劉穎敷搪,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體隘蝎,經(jīng)...
    沈念sama閱讀 45,619評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,819評(píng)論 3 336
  • 正文 我和宋清朗相戀三年襟企,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了嘱么。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,932評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡顽悼,死狀恐怖曼振,靈堂內(nèi)的尸體忽然破棺而出几迄,到底是詐尸還是另有隱情,我是刑警寧澤冰评,帶...
    沈念sama閱讀 35,655評(píng)論 5 346
  • 正文 年R本政府宣布映胁,位于F島的核電站,受9級(jí)特大地震影響甲雅,放射性物質(zhì)發(fā)生泄漏解孙。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,265評(píng)論 3 329
  • 文/蒙蒙 一抛人、第九天 我趴在偏房一處隱蔽的房頂上張望弛姜。 院中可真熱鬧,春花似錦妖枚、人聲如沸廷臼。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,871評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)荠商。三九已至,卻和暖如春续誉,著一層夾襖步出監(jiān)牢的瞬間莱没,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,994評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工屈芜, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留郊愧,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 48,095評(píng)論 3 370
  • 正文 我出身青樓井佑,卻偏偏與公主長(zhǎng)得像属铁,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子躬翁,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,884評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容

  • 本節(jié)繼續(xù)學(xué)習(xí)Python的基本語(yǔ)法焦蘑,主要內(nèi)容如下: 代碼注釋; 引號(hào)盒发; 連接符例嘱; 1. 代碼注釋目的: 1)增加代...
    老黃愛(ài)Python閱讀 386評(píng)論 0 0
  • 感冒 頭疼欲裂,一把鼻涕一把淚宁舰,身體上各種不爽拼卵,前段時(shí)間因?yàn)檠坌那椴皇娣髞?lái)又因?yàn)獒樉目赡芸赡苓€是怎樣 ...
    局外人ng閱讀 166評(píng)論 0 0
  • 陽(yáng)江哥仔閱讀 283評(píng)論 0 0