Android實(shí)現(xiàn)網(wǎng)絡(luò)多線程斷點(diǎn)續(xù)傳下載功能
我們編寫的是Andorid的HTTP協(xié)議多線程斷點(diǎn)下載應(yīng)用程序。直接使用單線程下載HTTP文件對(duì)我們來(lái)說(shuō)是一件非常簡(jiǎn)單的事。那么,多線程斷點(diǎn)需要什么功能?
1.多線程下載
2.支持?jǐn)帱c(diǎn)
使用多線程的好處:使用多線程下載會(huì)提升文件下載的速度
原理
多線程下載的原理就是將要下載的文件分成若干份,其中每份都使用一個(gè)單獨(dú)的線程進(jìn)行下載,這樣對(duì)于文件的下載速度自然就提高了許多。
既然要分成若干部分分工下載,自然要知道各個(gè)線程自己要下載的起始位置,與要下載的大小。所以我們要解決線程的分配與各個(gè)線程定位到下載的位置。
封裝
對(duì)于多線程下載我們可以將其封裝到一個(gè)工具類中DownUtil,向其中傳入下載的鏈接、文件存儲(chǔ)路徑、需要下載的線程數(shù)
分配線程
這里通過(guò)HttpURLConnection進(jìn)行網(wǎng)絡(luò)請(qǐng)求下載,通過(guò)getContentLength()方法獲取下載文件的總大小,再對(duì)其平均分配各個(gè)線程需要下載的大小。這樣就確定了下載的大小,下面就是定位到各個(gè)線程的開(kāi)始位置進(jìn)行下載,這里可以使用RandomAccessFile來(lái)追蹤定位到要下載的位置,它的seek()方法可以進(jìn)行定位。
線程下載
下面就是各個(gè)線程的下載DownThread,上面已經(jīng)得到了各個(gè)線程要下載的初始位置,所以可以通過(guò)獲取網(wǎng)絡(luò)請(qǐng)求的輸入流InputStream,通過(guò)skip()方法跳躍到指定位置進(jìn)行讀取數(shù)據(jù),再寫入到RandomAccessFile文件中
一、 編寫基本的UI,三個(gè)TextView,分別顯示文件名、下載進(jìn)度和下載速度,一個(gè)ProgressBar。二個(gè)Button,分別用于開(kāi)始下載、暫停下載和取消下載。
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" android:paddingBottom="@dimen/activity_vertical_margin" android:paddingLeft="@dimen/activity_horizontal_margin" android:paddingRight="@dimen/activity_horizontal_margin" android:paddingTop="@dimen/activity_vertical_margin" tools:context="com.example.linux.continuedownload.MainActivity"> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content"> <TextView android:id="@+id/textView" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <TextView android:layout_marginLeft="80dp" android:id="@+id/progress" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <TextView android:layout_marginLeft="80dp" android:id="@+id/speed" android:layout_width="wrap_content" android:layout_height="wrap_content" /> </LinearLayout> <ProgressBar android:visibility="invisible" android:id="@+id/progressBar" style="?android:attr/progressBarStyleHorizontal" android:layout_width="match_parent" android:layout_height="wrap_content" /> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content"> <Button android:id="@+id/start" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="開(kāi)始下載" /> <Button android:layout_marginLeft="20dp" android:id="@+id/stop" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="暫停下載" /> <Button android:layout_marginLeft="20dp" android:id="@+id/cancel" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="取消下載" /> </LinearLayout> </LinearLayout>
在onCreate方法中綁定開(kāi)始下載按鈕事件:點(diǎn)擊start按鈕,設(shè)置進(jìn)度條可見(jiàn),并且設(shè)置start的Action,啟動(dòng)服務(wù)。
startButton.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { textView.setText(fileInfo.getFileName()); progressBar.setVisibility(View.VISIBLE); // 通過(guò)Intent傳遞參數(shù)給service Intent intent = new Intent(MainActivity.this, DownloadService.class); intent.setAction(DownloadService.ACTION_START); intent.putExtra("fileInfo", fileInfo); startService(intent); } });
在onCreate方法中綁定暫停下載按鈕事件:點(diǎn)擊stop按鈕,設(shè)置stop的Action,啟動(dòng)服務(wù)。
stopButton.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { // 通過(guò)Intent傳遞參數(shù)給service Intent intent = new Intent(MainActivity.this, DownloadService.class); intent.setAction(DownloadService.ACTION_STOP); intent.putExtra("fileInfo", fileInfo); startService(intent); } });
在onCreate方法中綁定取消下載按鈕事件:點(diǎn)擊cancel按鈕,設(shè)置cancel的Action,啟動(dòng)服務(wù),之后更新UI。
cancelButton.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { // 通過(guò)Intent傳遞參數(shù)給service Intent intent = new Intent(MainActivity.this, DownloadService.class); intent.setAction(DownloadService.ACTION_CANCEL); intent.putExtra("fileInfo", fileInfo); startService(intent); // 更新textView和progressBar的顯示UI textView.setText(""); progressBar.setVisibility(View.INVISIBLE); progressView.setText(""); speedView.setText(""); } });
注冊(cè)廣播,用于Service向Activity傳遞一些下載進(jìn)度信息:
// 靜態(tài)注冊(cè)廣播 IntentFilter intentFilter = new IntentFilter(); intentFilter.addAction(DownloadService.ACTION_UPDATE); registerReceiver(broadcastReceiver, intentFilter); /** * 更新UI */ BroadcastReceiver broadcastReceiver = new BroadcastReceiver() { @Override public void onReceive(Context context, Intent intent) { if (DownloadService.ACTION_UPDATE.equals(intent.getAction())) { int finished = intent.getIntExtra("finished", 0); int speed = intent.getIntExtra("speed", 0); Log.i("Main", finished + ""); progressBar.setProgress(finished); progressView.setText(finished + "%"); speedView.setText(speed + "KB/s"); } } };
三、 在AndroidManifest.xm文件中聲明權(quán)限,定義服務(wù)
<service android:name="com.huhx.services.DownloadService" android:exported="true" /> <uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
總結(jié)
多線程的關(guān)鍵就是分配好需要下載的進(jìn)程,定位進(jìn)程下載的準(zhǔn)確位置,獲取輸入流讀取數(shù)據(jù),同時(shí)寫入到文件的相應(yīng)位置。可以借助RandomAccessFile來(lái)進(jìn)行定位。
當(dāng)然也并非開(kāi)的線程數(shù)越多下載的速度也就越快,因?yàn)榫€程越多對(duì)于程序處理這些線程也是一種負(fù)擔(dān),過(guò)多的話反而會(huì)降低下載的速度,所以要合理運(yùn)用。
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
- Android多線程斷點(diǎn)續(xù)傳下載實(shí)現(xiàn)代碼
- Android 使用AsyncTask實(shí)現(xiàn)多線程斷點(diǎn)續(xù)傳
- Android 使用AsyncTask實(shí)現(xiàn)多任務(wù)多線程斷點(diǎn)續(xù)傳下載
- android實(shí)現(xiàn)多線程斷點(diǎn)續(xù)傳功能
- Android多線程斷點(diǎn)續(xù)傳下載示例詳解
- Android FTP 多線程斷點(diǎn)續(xù)傳下載\上傳的實(shí)例
- Android多線程+單線程+斷點(diǎn)續(xù)傳+進(jìn)度條顯示下載功能
- android實(shí)現(xiàn)多線程下載文件(支持暫停、取消、斷點(diǎn)續(xù)傳)
- Android實(shí)現(xiàn)網(wǎng)絡(luò)多線程斷點(diǎn)續(xù)傳下載實(shí)例
- Android實(shí)現(xiàn)多線程斷點(diǎn)續(xù)傳
相關(guān)文章
Android打造流暢九宮格抽獎(jiǎng)活動(dòng)效果
抽獎(jiǎng)活動(dòng)有很多種形式,轉(zhuǎn)盤抽獎(jiǎng),九宮格抽獎(jiǎng),刮刮卡抽獎(jiǎng),這篇文章主要為大家詳細(xì)介紹了如何打造流暢九宮格抽獎(jiǎng)活動(dòng)效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2016-11-11Android仿一號(hào)店貨物詳情輪播圖動(dòng)畫效果
這篇文章主要為大家詳細(xì)介紹了Android-仿一號(hào)店貨物詳情輪播圖動(dòng)畫效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-06-06從"Show?tabs"了解Android?Input系統(tǒng)
這篇文章主要介紹了從"Show?tabs"了解Android?Input系統(tǒng)的相關(guān)資料,需要的朋友可以參考下2023-01-01Android開(kāi)發(fā)自學(xué)筆記(六):聲明權(quán)限和Activity
這篇文章主要介紹了Android開(kāi)發(fā)自學(xué)筆記(六):聲明權(quán)限和Activity,本文是上一篇的補(bǔ)充,需要的朋友可以參考下2015-04-04android textview設(shè)置字體的行距和字間距
這篇文章主要介紹了android textview設(shè)置字體的行距和字間距的方法,非常簡(jiǎn)單實(shí)用,有需要的小伙伴可以參考下2016-05-05flutter InheritedWidget使用方法總結(jié)
這篇文章主要為大家介紹了flutter InheritedWidget使用方法總結(jié)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-11-11Android 消息機(jī)制問(wèn)題總結(jié)
本文主要介紹Android 消息機(jī)制,這里整理了消息機(jī)制的詳細(xì)資料,和經(jīng)常出現(xiàn)的問(wèn)題,希望能幫助大家對(duì)消息機(jī)制的理解2016-08-08Android應(yīng)用中炫酷的橫向和環(huán)形進(jìn)度條的實(shí)例分享
這篇文章主要介紹了Android應(yīng)用中炫酷的橫向和圓形進(jìn)度條的實(shí)例分享,文中利用了一些GitHub上的插件進(jìn)行改寫,也是一片很好的二次開(kāi)發(fā)教學(xué),需要的朋友可以參考下2016-04-04Eclipse下配置Ant腳本并自動(dòng)打包帶簽名的Android apk
這篇文章主要介紹了Eclipse下配置Ant腳本并自動(dòng)打包帶簽名的Android apk的相關(guān)資料,需要的朋友可以參考下2016-03-03