轉載:http://blog.csdn.net/youmingyu/article/details/52583409
這個demo演示從網上下載文件並保存到手機,demo中可以下載一個XML文件並在Console窗口輸出,還可以下載一個MP3文件並保存到手機存儲目錄中的BoBoMusic文件夾中,下載保存成功會返回:0。(XML和MP3文件我已經傳到百度的對象存儲中,方便大家調用demo中的URL調試)
完整demo:下載地址
首先:在Manifest文件中添加訪問網絡和讀寫存儲的權限
<uses-permission
android:name="android.permission.INTERNET"/>
<uses-permission
android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
然後:文件工具類 FileUtils.java
- package fk.androiddemo_009;
- import android.os.Environment;
- import java.io.File;
- import java.io.FileOutputStream;
- import java.io.IOException;
- import java.io.InputStream;
- import java.io.OutputStream;
- /**
- * Created by Administrator on 2016/9/14.
- */
- public class FileUtils {
- private String SDCardRoot;
- public FileUtils(){
- //得到當前外部存儲設備的目錄
- SDCardRoot= Environment.getExternalStorageDirectory()+File.separator;
- //File.separator爲文件分隔符”/“,方便之後在目錄下創建文件
- }
- //在SD卡上創建文件
- public File createFileInSDCard(String fileName,String dir) throws IOException {
- File file=new File(SDCardRoot+dir+File.separator+fileName);
- file.createNewFile();
- return file;
- }
- //在SD卡上創建目錄
- public File createSDDir(String dir)throws IOException{
- File dirFile=new File(SDCardRoot+dir);
- dirFile.mkdir();//mkdir()只能創建一層文件目錄,mkdirs()可以創建多層文件目錄
- return dirFile;
- }
- //判斷文件是否存在
- public boolean isFileExist(String fileName,String dir){
- File file=new File(SDCardRoot+dir+File.separator+fileName);
- return file.exists();
- }
- //將一個InoutStream裏面的數據寫入到SD卡中
- public File write2SDFromInput(String fileName,String dir,InputStream input){
- File file=null;
- OutputStream output=null;
- try {
- //創建目錄
- createSDDir(dir);
- //創建文件
- file=createFileInSDCard(fileName,dir);
- //寫數據流
- output=new FileOutputStream(file);
- byte buffer[]=new byte[4*1024];//每次存4K
- int temp;
- //寫入數據
- while((temp=input.read(buffer))!=-1){
- output.write(buffer,0,temp);
- }
- output.flush();
- } catch (Exception e) {
- System.out.println("寫數據異常:"+e);
- }
- finally{
- try {
- output.close();
- } catch (Exception e2) {
- System.out.println(e2);
- }
- }
- return file;
- }
- }
下載工具類:HttpDownloader.java
- package fk.androiddemo_009;
- import java.io.BufferedReader;
- import java.io.File;
- import java.io.IOException;
- import java.io.InputStream;
- import java.io.InputStreamReader;
- import java.net.HttpURLConnection;
- import java.net.URL;
- /**
- * Created by Administrator on 2016/9/14.
- */
- public class HttpDownloader {
- String line=null;
- StringBuffer strBuffer=new StringBuffer();
- BufferedReader bufferReader=null;
- //下載小型的文檔文件,返回文檔的String字符串
- public String downloadFiles(String urlStr){
- try {
- InputStream inputStream=getInputStreamFromUrl(urlStr);
- bufferReader=new BufferedReader(new InputStreamReader(inputStream));
- while((line=bufferReader.readLine())!=null){
- strBuffer.append(line+'\n');
- }
- } catch (Exception e) {
- strBuffer.append("something is wrong!!");
- System.out.println("讀取數據異常:"+e);
- } finally{
- try {
- bufferReader.close();
- } catch (Exception e) {
- strBuffer.append("something is wrong!!");
- e.printStackTrace();
- }
- }
- return strBuffer.toString();
- }
- //可以下載任意文件,例如MP3,並把文件存儲在制定目錄(-1:下載失敗,0:下載成功,1:文件已存在)
- public int downloadFiles(String urlStr,String path,String fileName){
- try {
- FileUtils fileUtils=new FileUtils();
- if(fileUtils.isFileExist(fileName,path)) return 1;//判斷文件是否存在
- else{
- InputStream inputStream=getInputStreamFromUrl(urlStr);
- File resultFile=fileUtils.write2SDFromInput(fileName,path,inputStream);
- if(resultFile==null) return -1;
- }
- } catch (Exception e) {
- System.out.println("讀寫數據異常:"+e);
- return -1;
- }
- return 0;
- }
- public InputStream getInputStreamFromUrl(String urlStr)throws IOException {
- //創建一個URL對象
- URL url=new URL(urlStr);
- //創建一個HTTP鏈接
- HttpURLConnection urlConn=(HttpURLConnection)url.openConnection();
- //使用IO流獲取數據
- InputStream inputStream=urlConn.getInputStream();
- return inputStream;
- }
- }
主界面:MainActivity.java
- package fk.androiddemo_009;
- import android.support.v7.app.AppCompatActivity;
- import android.os.Bundle;
- import android.view.View;
- import android.widget.Button;
- //1,在Manifest文件中註冊Internet和讀寫SDCard的權限
- //2,下載不能在主線程中進行,要開分線程
- public class MainActivity extends AppCompatActivity implements View.OnClickListener{
- Button but1,but2;
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.activity_main);
- but1=(Button)findViewById(R.id.but1);
- but1.setOnClickListener(this);
- but2=(Button)findViewById(R.id.but2);
- but2.setOnClickListener(this);
- }
- @Override
- public void onClick(View v) {
- if(v==but1){
- new downloadFileThread().start();
- }else if(v==but2){
- new downloadMP3Thread().start();
- }
- }
- class downloadFileThread extends Thread{
- public void run(){
- HttpDownloader httpDownloader=new HttpDownloader();
- String fileData=httpDownloader.downloadFiles("http://mystudy.bj.bcebos.com/AndroidDemo_009.xml");
- System.out.println(fileData);
- }
- }
- class downloadMP3Thread extends Thread{
- public void run(){
- HttpDownloader httpDownloader=new HttpDownloader();
- int downloadResult=httpDownloader.downloadFiles(
- "http://fengkui.bj.bcebos.com/%E8%B6%B3%E9%9F%B3.mp3","BoBoMusic","足音.mp3");
- System.out.println("下載結果:"+downloadResult);
- }
- }
- }
運行截圖:
PS:有一點需要注意,在Android6.0及以上的系統,由於權限申請的改動,此demo安裝後需要在APP管理中手動打開存儲權限才能正常運行,否則無法向存儲器中寫數據,具體原因可以參考這兩篇博文:
http://unclechen.github.io/2016/03/05/Android6.0%E8%BF%90%E8%A1%8C%E6%97%B6%E6%9D%83%E9%99%90%E7%AE%80%E4%BB%8B/
虛擬機中打開存儲權限的位置:
如果想要在虛擬機上查看下載的MP3文件,可以在SDK目錄下的platform-tools中利用adb.exe查看,命令如下,原來亦可以使用DDMS,但是現在需要打開權限挺麻煩。