`
jean7155
  • 浏览: 61274 次
  • 性别: Icon_minigender_2
  • 来自: 上海
社区版块
存档分类
最新评论

使用后台服务下载文件的例子

阅读更多
最近做了一个DEMO, 是通过httpURLConnection服务来下载文件。 大致的设计思路是这样的:
1. 主Activity,显示需要下载的文件名,并通过ProgressDialog来显示下载进度。
2. 后台服务IntentService进行主要的下载操作,先通过HttpURLConnection来获取远程服务的InputStream, 然后将获取的InputStream写入设备的sdCard中。
3. 通过ResultReceiver传递下载的完成信息给ProgressDialog,使其能及时更新下载进度。

具体的代码:
1. 老样子,在AndroidManifest.xml中设置对因特网的访问权限,和对SDCard的操作权限
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission>
<uses-permission android:name="android.permission.INTERNET"></uses-permission>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"></uses-permission>


2. 其次,需要在AndroidManifest.xml中设置Activity和Service
<activity
            android:name="cn.sh.ideal.activity.DownloadActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
</activity>
        
<service android:name="cn.sh.ideal.service.DownloadService"/>


3. 在DownloadActivity中,显示需要下载的文件名,点击文件名,调用DownloadService进行文件的下载,并在界面中产生ProgressDialog进度
				if(fileRealName!=null && fileRealName.trim().length()>0){
					
					fileName = fileRealName;
					
					try {
						url = ToolsUtil.getIpAddress() + URLEncoder.encode(fileRealName,"UTF-8");
					} catch (UnsupportedEncodingException e) {
						e.printStackTrace();
					}
					
					progressDialog = new ProgressDialog(DownloadActivity.this);
					progressDialog.setTitle(getResources().getString(R.string.download_title));
					progressDialog.setMessage(getResources().getString(R.string.download_message));
					progressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);

					progressDialog.show();
					
					intent = new Intent(DownloadActivity.this, DownloadService.class);
					intent.putExtra("url", url);
					intent.putExtra("filename", fileName);
					intent.putExtra("receiver", new DownloadReceiver(new Handler()));
					intent.setAction("start");
					startService(intent);
					
				}


4. DownloadService 对文件进行下载
	protected void onHandleIntent(Intent intent) {
		 String urlToDownload = intent.getStringExtra("url");
		 String filenameToSave = intent.getStringExtra("filename");
		 
	     ResultReceiver receiver = (ResultReceiver) intent.getParcelableExtra("receiver");
	     
	 	 String sdPath = "";
		 int results = 0;
		 String infos = "";
		 
		 InputStream input = null;
		 OutputStream output = null;
     
	     try {
                 //设备中是否存在SDCard,如果不存在则抛出异常
	    	 isSDCard();
                 //设备是否可连接,如果不可链接则抛出异常
	    	 isConnected();
	    	 
	    	 sdPath = Environment.getExternalStorageDirectory() + "/" + Constants.DOWNLOAD_PATH;
                 // SDCard中的存储路径是否存在,如果不存在则创建
	    	 File dir = new File(sdPath);
	    	 if(!dir.exists()) createSDDir(sdPath);
	    	 
	    	 sdPath = Environment.getExternalStorageDirectory() + "/" + Constants.DOWNLOAD_PATH + "/" + filenameToSave;
	    	 
                 // 计算需要下载的文件的长度
	    	 long totalSize = getRemoteFilesize(urlToDownload);
	    	 
                 // 计算SDCard的剩余空间是否足够保存下载文件。如果不够,则抛出异常 
	    	 isSDCardFreeSizeAvailable((int)totalSize);
	    	 
    		 URL url = new URL(urlToDownload);
    		 connection = (HttpURLConnection) url.openConnection();
    		 connection.setConnectTimeout(CONNECT_TIME_OUT);
	         
    		 connection.connect();
	         
                 // 获取Http服务的返回信息,如果服务信息为HTTP_OK, HTTP_PARTIAL, 则可进行下载服务,否则抛出异常
    		 int code = getHttpResponseMessage(connection);
    		 Log.i(TAG,"httpReturnType=" + code);
	            
    		 input = new BufferedInputStream(connection.getInputStream());

   			 output =new FileOutputStream(sdPath);

   			 byte data[] = new byte[1024];
   			 long total = 0l;
   			 int count;
   			 while ((count = input.read(data)) != -1) {
   				 total += count;
	                
   				 Bundle resultData = new Bundle();
   				 resultData.putInt("progress" ,(int) (total * 100 / totalSize));
   				 receiver.send(UPDATE_PROGRESS, resultData);
   				 output.write(data, 0, count);
   			 }

   			 output.flush();
   			 output.close();
   			 input.close();
    			 
   	         results = DOWNLOAD_SUCCESS;
	     }
	     catch(SDCardNotAvailableException sdex){
	    	 results = DOWNLOAD_ERROR;
	    	 infos = getResources().getString(R.string.download_error_sdcard_not_available);
	     }
	     catch(AndroidNoActiveConnectionException aex){
	    	 results = DOWNLOAD_ERROR;
	    	 infos = getResources().getString(R.string.download_error_no_active_connection);
		 }
		 catch(SDCardFreeNotAvailableException sdfex){
			 infos =  getResources().getString(R.string.download_error_sdcard_not_free);
	    	 results = DOWNLOAD_ERROR; 
		 }
		 catch(HttpServiceException rex){
	    	 results = DOWNLOAD_ERROR;
	    	 infos = getResources().getString(R.string.download_error_http_service);
		 }
		 catch(FileNotFoundException fex){
			 results = DOWNLOAD_ERROR;
			 infos = getResources().getString(R.string.download_error_file_not_found);
		 }catch(IOException ioex){
			 results = DOWNLOAD_ERROR;
			 infos = getResources().getString(R.string.download_error_io);
		 }
		 catch(Exception ex){
			 results = DOWNLOAD_ERROR;
			 infos = getResources().getString(R.string.download_error_others);
			 Log.e(TAG,ex.getLocalizedMessage());
		 }
		 finally{
			 if(input!=null)
				try {
					input.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			 if(output!=null)
				try {
					output.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			 
			 if(connection!=null) connection.disconnect();
			 
	         Bundle resultData = new Bundle();
	         resultData.putInt("progress" ,results);
	         
	         if(infos!=null && infos.trim().length()>0)
	        	 resultData.putString("resultMessage", infos);
	         
	         receiver.send(UPDATE_PROGRESS, resultData);
	     }

               

5. 在DownloadActivity中添加DownloadReceiver类,用以接收DownloadService的下载进度信息和错误信息
	private class DownloadReceiver extends ResultReceiver{
	    public DownloadReceiver(Handler handler) {
	        super(handler);
	    }

	    protected void onReceiveResult(int resultCode, Bundle resultData) {
	        super.onReceiveResult(resultCode, resultData);
	        
	        if (resultCode == DownloadService.UPDATE_PROGRESS) {
	            int progress = resultData.getInt("progress");
	            
	            if(progress == DownloadService.DOWNLOAD_ERROR){
	            	String infos = resultData.getString("resultMessage");
	            	progressDialog.dismiss();
	            	Toast.makeText(DownloadActivity.this, infos, Toast.LENGTH_SHORT).show();

	            }else if(progress == DownloadService.DOWNLOAD_SUCCESS){
	            	progressDialog.dismiss();
	            
	            }else{
	            	progressDialog.setProgress(progress);
	            }
	        }
	    }


附件中提供了这个DEMO的完整代码。
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics