博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
webview实现文件下载的功能
阅读量:4116 次
发布时间:2019-05-25

本文共 16227 字,大约阅读时间需要 54 分钟。

WebView控制调用相应的WEB页面进行展示。当碰到页面有下载链接的时候,点击上去是一点反应都没有的。原来是因为WebView默认没有开启文件下载的功能,如果要实现文件下载的功能,需要设置WebView的DownloadListener,通过实现自己的DownloadListener来实现文件的下载。具体操作如下: 


1、设置WebView的DownloadListener: 

    webView.setDownloadListener(new MyWebViewDownLoadListener()); 


2、实现MyWebViewDownLoadListener这个类,具体可以如下这样:  

[java]
  1. private class MyWebViewDownLoadListener implements DownloadListener{  
  2.   
  3.         @Override  
  4.         public void onDownloadStart(String url, String userAgent, String contentDisposition, String mimetype,  
  5.                                     long contentLength) {             
  6.             Log.i("tag""url="+url);             
  7.             Log.i("tag""userAgent="+userAgent);  
  8.             Log.i("tag""contentDisposition="+contentDisposition);           
  9.             Log.i("tag""mimetype="+mimetype);  
  10.             Log.i("tag""contentLength="+contentLength);  
  11.             Uri uri = Uri.parse(url);  
  12.             Intent intent = new Intent(Intent.ACTION_VIEW, uri);  
  13.             startActivity(intent);             
  14.         }  
  15.     }  
private class MyWebViewDownLoadListener implements DownloadListener{        @Override        public void onDownloadStart(String url, String userAgent, String contentDisposition, String mimetype,                                    long contentLength) {        	        	Log.i("tag", "url="+url);        	        	Log.i("tag", "userAgent="+userAgent);        	Log.i("tag", "contentDisposition="+contentDisposition);        	        	Log.i("tag", "mimetype="+mimetype);        	Log.i("tag", "contentLength="+contentLength);            Uri uri = Uri.parse(url);            Intent intent = new Intent(Intent.ACTION_VIEW, uri);            startActivity(intent);        	         }    }
  这只是调用系统中已经内置的浏览器进行下载,还没有WebView本身进行的文件下载,不过,这也基本上满足我们的应用场景了。 


我在项目中的运用 

项目要求这样: 

1,需要使用WebView加载一个网页; 

2,网页中有文件下载的链接,点击后需要下载文件到SDcard; 

3,然后自动打开文件; 

下面是具体解决办法 

第一步,对WebView进行一系列设置。
[java]
  1. WebView webview=(WebView)layout.findViewById(R.id.webview);  
  2.                 webview.getSettings().setJavaScriptEnabled(true);  
  3.                 webview.setWebChromeClient(new MyWebChromeClient());  
  4.                 webview.requestFocus();  
  5. //              webview.loadUrl("file:///android_asset/risktest.html");   
  6.                 webview.loadUrl(jcrs_sub.get(position).addr);  
  7.                 // 设置web视图客户端   
  8.                 webview.setWebViewClient(new MyWebViewClient());  
  9.                 webview.setDownloadListener(new MyWebViewDownLoadListener());  
  10.   
  11. //内部类   
  12. public class MyWebViewClient extends WebViewClient {  
  13.         // 如果页面中链接,如果希望点击链接继续在当前browser中响应,   
  14.         // 而不是新开Android的系统browser中响应该链接,必须覆盖 webview的WebViewClient对象。   
  15.         public boolean shouldOverviewUrlLoading(WebView view, String url) {  
  16.             L.i("shouldOverviewUrlLoading");  
  17.             view.loadUrl(url);  
  18.             return true;  
  19.         }  
  20.   
  21.         public void onPageStarted(WebView view, String url, Bitmap favicon) {  
  22.             L.i("onPageStarted");  
  23.             showProgress();  
  24.         }  
  25.   
  26.         public void onPageFinished(WebView view, String url) {  
  27.             L.i("onPageFinished");  
  28.             closeProgress();  
  29.         }  
  30.   
  31.         public void onReceivedError(WebView view, int errorCode,  
  32.                 String description, String failingUrl) {  
  33.             L.i("onReceivedError");  
  34.             closeProgress();  
  35.         }  
  36.     }  
  37.   
  38. // 如果不做任何处理,浏览网页,点击系统“Back”键,整个Browser会调用finish()而结束自身,   
  39.     // 如果希望浏览的网 页回退而不是推出浏览器,需要在当前Activity中处理并消费掉该Back事件。   
  40.     public boolean onKeyDown(int keyCode, KeyEvent event) {  
  41.         // if((keyCode==KeyEvent.KEYCODE_BACK)&&webview.canGoBack()){   
  42.         // webview.goBack();   
  43.         // return true;   
  44.         // }   
  45.         return false;  
  46.     }  
WebView webview=(WebView)layout.findViewById(R.id.webview);				webview.getSettings().setJavaScriptEnabled(true);				webview.setWebChromeClient(new MyWebChromeClient());				webview.requestFocus();//				webview.loadUrl("file:///android_asset/risktest.html");				webview.loadUrl(jcrs_sub.get(position).addr);				// 设置web视图客户端				webview.setWebViewClient(new MyWebViewClient());				webview.setDownloadListener(new MyWebViewDownLoadListener());//内部类public class MyWebViewClient extends WebViewClient {		// 如果页面中链接,如果希望点击链接继续在当前browser中响应,		// 而不是新开Android的系统browser中响应该链接,必须覆盖 webview的WebViewClient对象。		public boolean shouldOverviewUrlLoading(WebView view, String url) {			L.i("shouldOverviewUrlLoading");			view.loadUrl(url);			return true;		}		public void onPageStarted(WebView view, String url, Bitmap favicon) {			L.i("onPageStarted");			showProgress();		}		public void onPageFinished(WebView view, String url) {			L.i("onPageFinished");			closeProgress();		}		public void onReceivedError(WebView view, int errorCode,				String description, String failingUrl) {			L.i("onReceivedError");			closeProgress();		}	}// 如果不做任何处理,浏览网页,点击系统“Back”键,整个Browser会调用finish()而结束自身,	// 如果希望浏览的网 页回退而不是推出浏览器,需要在当前Activity中处理并消费掉该Back事件。	public boolean onKeyDown(int keyCode, KeyEvent event) {		// if((keyCode==KeyEvent.KEYCODE_BACK)&&webview.canGoBack()){		// webview.goBack();		// return true;		// }		return false;	}
第二步,起线程开始下载文件。
[java]
  1. //内部类   
  2. private class MyWebViewDownLoadListener implements DownloadListener {  
  3.   
  4.         @Override  
  5.         public void onDownloadStart(String url, String userAgent, String contentDisposition, String mimetype,  
  6.                                     long contentLength) {  
  7.             if(!Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)){  
  8.                 Toast t=Toast.makeText(mContext, "需要SD卡。", Toast.LENGTH_LONG);  
  9.                 t.setGravity(Gravity.CENTER, 00);  
  10.                 t.show();  
  11.                 return;  
  12.             }  
  13.             DownloaderTask task=new DownloaderTask();  
  14.             task.execute(url);  
  15.         }  
  16.   
  17.     }  
  18.     //内部类   
  19.     private class DownloaderTask extends AsyncTask<String, Void, String> {   
  20.   
  21.         public DownloaderTask() {   
  22.         }  
  23.   
  24.         @Override  
  25.         protected String doInBackground(String... params) {  
  26.             // TODO Auto-generated method stub   
  27.             String url=params[0];  
  28. //          Log.i("tag", "url="+url);   
  29.             String fileName=url.substring(url.lastIndexOf("/")+1);  
  30.             fileName=URLDecoder.decode(fileName);  
  31.             Log.i("tag""fileName="+fileName);  
  32.               
  33.             File directory=Environment.getExternalStorageDirectory();  
  34.             File file=new File(directory,fileName);  
  35.             if(file.exists()){  
  36.                 Log.i("tag""The file has already exists.");  
  37.                 return fileName;  
  38.             }  
  39.             try {    
  40.                 HttpClient client = new DefaultHttpClient();    
  41. //                client.getParams().setIntParameter("http.socket.timeout",3000);//设置超时   
  42.                 HttpGet get = new HttpGet(url);    
  43.                 HttpResponse response = client.execute(get);  
  44.                 if(HttpStatus.SC_OK==response.getStatusLine().getStatusCode()){  
  45.                     HttpEntity entity = response.getEntity();  
  46.                     InputStream input = entity.getContent();  
  47.                       
  48.                     writeToSDCard(fileName,input);  
  49.                       
  50.                     input.close();  
  51. //                  entity.consumeContent();   
  52.                     return fileName;    
  53.                 }else{  
  54.                     return null;  
  55.                 }  
  56.             } catch (Exception e) {    
  57.                 e.printStackTrace();  
  58.                 return null;  
  59.             }  
  60.         }  
  61.   
  62.         @Override  
  63.         protected void onCancelled() {  
  64.             // TODO Auto-generated method stub   
  65.             super.onCancelled();  
  66.         }  
  67.   
  68.         @Override  
  69.         protected void onPostExecute(String result) {  
  70.             // TODO Auto-generated method stub   
  71.             super.onPostExecute(result);  
  72.             closeProgressDialog();  
  73.             if(result==null){  
  74.                 Toast t=Toast.makeText(mContext, "连接错误!请稍后再试!", Toast.LENGTH_LONG);  
  75.                 t.setGravity(Gravity.CENTER, 00);  
  76.                 t.show();  
  77.                 return;  
  78.             }  
  79.               
  80.             Toast t=Toast.makeText(mContext, "已保存到SD卡。", Toast.LENGTH_LONG);  
  81.             t.setGravity(Gravity.CENTER, 00);  
  82.             t.show();  
  83.             File directory=Environment.getExternalStorageDirectory();  
  84.             File file=new File(directory,result);  
  85.             Log.i("tag""Path="+file.getAbsolutePath());  
  86.               
  87.             Intent intent = getFileIntent(file);  
  88.               
  89.             startActivity(intent);  
  90.                   
  91.         }  
  92.   
  93.         @Override  
  94.         protected void onPreExecute() {  
  95.             // TODO Auto-generated method stub   
  96.             super.onPreExecute();  
  97.             showProgressDialog();  
  98.         }  
  99.   
  100.         @Override  
  101.         protected void onProgressUpdate(Void... values) {  
  102.             // TODO Auto-generated method stub   
  103.             super.onProgressUpdate(values);  
  104.         }   
  105.   
  106.           
  107.     }   
//内部类private class MyWebViewDownLoadListener implements DownloadListener {        @Override        public void onDownloadStart(String url, String userAgent, String contentDisposition, String mimetype,                                    long contentLength) {        	if(!Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)){        		Toast t=Toast.makeText(mContext, "需要SD卡。", Toast.LENGTH_LONG);				t.setGravity(Gravity.CENTER, 0, 0);				t.show();				return;        	}			DownloaderTask task=new DownloaderTask();			task.execute(url);        }    }	//内部类	private class DownloaderTask extends AsyncTask
{ public DownloaderTask() { } @Override protected String doInBackground(String... params) { // TODO Auto-generated method stub String url=params[0];// Log.i("tag", "url="+url); String fileName=url.substring(url.lastIndexOf("/")+1); fileName=URLDecoder.decode(fileName); Log.i("tag", "fileName="+fileName); File directory=Environment.getExternalStorageDirectory(); File file=new File(directory,fileName); if(file.exists()){ Log.i("tag", "The file has already exists."); return fileName; } try { HttpClient client = new DefaultHttpClient(); // client.getParams().setIntParameter("http.socket.timeout",3000);//设置超时 HttpGet get = new HttpGet(url); HttpResponse response = client.execute(get); if(HttpStatus.SC_OK==response.getStatusLine().getStatusCode()){ HttpEntity entity = response.getEntity(); InputStream input = entity.getContent(); writeToSDCard(fileName,input); input.close();// entity.consumeContent(); return fileName; }else{ return null; } } catch (Exception e) { e.printStackTrace(); return null; } } @Override protected void onCancelled() { // TODO Auto-generated method stub super.onCancelled(); } @Override protected void onPostExecute(String result) { // TODO Auto-generated method stub super.onPostExecute(result); closeProgressDialog(); if(result==null){ Toast t=Toast.makeText(mContext, "连接错误!请稍后再试!", Toast.LENGTH_LONG); t.setGravity(Gravity.CENTER, 0, 0); t.show(); return; } Toast t=Toast.makeText(mContext, "已保存到SD卡。", Toast.LENGTH_LONG); t.setGravity(Gravity.CENTER, 0, 0); t.show(); File directory=Environment.getExternalStorageDirectory(); File file=new File(directory,result); Log.i("tag", "Path="+file.getAbsolutePath()); Intent intent = getFileIntent(file); startActivity(intent); } @Override protected void onPreExecute() { // TODO Auto-generated method stub super.onPreExecute(); showProgressDialog(); } @Override protected void onProgressUpdate(Void... values) { // TODO Auto-generated method stub super.onProgressUpdate(values); } }
第三步,实现一些工具方法。 

[java]
  1. <SPAN style="FONT-FAMILY: Helvetica, Tahoma, Arial, sans-serif">private ProgressDialog mDialog;  
  2.     private void showProgressDialog(){  
  3.         if(mDialog==null){  
  4.             mDialog = new ProgressDialog(mContext);    
  5.             mDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);//设置风格为圆形进度条     
  6.             mDialog.setMessage("正在加载 ,请等待...");    
  7.             mDialog.setIndeterminate(false);//设置进度条是否为不明确     
  8.             mDialog.setCancelable(true);//设置进度条是否可以按退回键取消     
  9.             mDialog.setCanceledOnTouchOutside(false);  
  10.             mDialog.setOnDismissListener(new OnDismissListener() {  
  11.                   
  12.                 @Override  
  13.                 public void onDismiss(DialogInterface dialog) {  
  14.                     // TODO Auto-generated method stub   
  15.                     mDialog=null;  
  16.                 }  
  17.             });  
  18.             mDialog.show();  
  19.               
  20.         }  
  21.     }  
  22.     private void closeProgressDialog(){  
  23.         if(mDialog!=null){  
  24.             mDialog.dismiss();  
  25.             mDialog=null;  
  26.         }  
  27.     }  
  28.      public Intent getFileIntent(File file){  
  29. //       Uri uri = Uri.parse("http://m.ql18.com.cn/hpf10/1.pdf");   
  30.         Uri uri = Uri.fromFile(file);  
  31.         String type = getMIMEType(file);  
  32.         Log.i("tag""type="+type);  
  33.         Intent intent = new Intent("android.intent.action.VIEW");  
  34.         intent.addCategory("android.intent.category.DEFAULT");  
  35.         intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);  
  36.         intent.setDataAndType(uri, type);  
  37.         return intent;  
  38.       }  
  39.        
  40.     public void writeToSDCard(String fileName,InputStream input){  
  41.           
  42.         if(Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)){  
  43.             File directory=Environment.getExternalStorageDirectory();  
  44.             File file=new File(directory,fileName);  
  45. //          if(file.exists()){   
  46. //              Log.i("tag", "The file has already exists.");   
  47. //              return;   
  48. //          }   
  49.             try {  
  50.                 FileOutputStream fos = new FileOutputStream(file);  
  51.                 byte[] b = new byte[2048];  
  52.                 int j = 0;  
  53.                 while ((j = input.read(b)) != -1) {  
  54.                     fos.write(b, 0, j);  
  55.                 }  
  56.                 fos.flush();  
  57.                 fos.close();  
  58.             } catch (FileNotFoundException e) {  
  59.                 // TODO Auto-generated catch block   
  60.                 e.printStackTrace();  
  61.             } catch (IOException e) {  
  62.                 // TODO Auto-generated catch block   
  63.                 e.printStackTrace();  
  64.             }  
  65.         }else{  
  66.             Log.i("tag""NO SDCard.");  
  67.         }  
  68.     }  
  69.       
  70.     private String getMIMEType(File f){     
  71.       String type="";    
  72.       String fName=f.getName();    
  73.       /* 取得扩展名 */    
  74.       String end=fName.substring(fName.lastIndexOf(".")+1,fName.length()).toLowerCase();  
  75.         
  76.       /* 依扩展名的类型决定MimeType */  
  77.       if(end.equals("pdf")){  
  78.           type = "application/pdf";//   
  79.       }  
  80.       else if(end.equals("m4a")||end.equals("mp3")||end.equals("mid")||    
  81.       end.equals("xmf")||end.equals("ogg")||end.equals("wav")){    
  82.         type = "audio/*";     
  83.       }    
  84.       else if(end.equals("3gp")||end.equals("mp4")){    
  85.         type = "video/*";    
  86.       }    
  87.       else if(end.equals("jpg")||end.equals("gif")||end.equals("png")||    
  88.       end.equals("jpeg")||end.equals("bmp")){    
  89.         type = "image/*";    
  90.       }    
  91.       else if(end.equals("apk")){     
  92.         /* android.permission.INSTALL_PACKAGES */     
  93.         type = "application/vnd.android.package-archive";   
  94.       }  
  95. //      else if(end.equals("pptx")||end.equals("ppt")){   
  96. //        type = "application/vnd.ms-powerpoint";    
  97. //      }else if(end.equals("docx")||end.equals("doc")){   
  98. //        type = "application/vnd.ms-word";   
  99. //      }else if(end.equals("xlsx")||end.equals("xls")){   
  100. //        type = "application/vnd.ms-excel";   
  101. //      }   
  102.       else{  
  103. //        /*如果无法直接打开,就跳出软件列表给用户选择 */     
  104.         type="*/*";  
  105.       }  
  106.       return type;  
  107.     }   </SPAN>  
private ProgressDialog mDialog;	private void showProgressDialog(){		if(mDialog==null){			mDialog = new ProgressDialog(mContext);  			mDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);//设置风格为圆形进度条  			mDialog.setMessage("正在加载 ,请等待...");  			mDialog.setIndeterminate(false);//设置进度条是否为不明确  			mDialog.setCancelable(true);//设置进度条是否可以按退回键取消  			mDialog.setCanceledOnTouchOutside(false);			mDialog.setOnDismissListener(new OnDismissListener() {								@Override				public void onDismiss(DialogInterface dialog) {					// TODO Auto-generated method stub					mDialog=null;				}			});			mDialog.show();					}	}	private void closeProgressDialog(){		if(mDialog!=null){			mDialog.dismiss();			mDialog=null;		}	}	 public Intent getFileIntent(File file){//		 Uri uri = Uri.parse("http://m.ql18.com.cn/hpf10/1.pdf");		Uri uri = Uri.fromFile(file);		String type = getMIMEType(file);		Log.i("tag", "type="+type);	    Intent intent = new Intent("android.intent.action.VIEW");	    intent.addCategory("android.intent.category.DEFAULT");	    intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);	    intent.setDataAndType(uri, type);	    return intent;	  }	 	public void writeToSDCard(String fileName,InputStream input){				if(Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)){			File directory=Environment.getExternalStorageDirectory();			File file=new File(directory,fileName);//			if(file.exists()){//				Log.i("tag", "The file has already exists.");//				return;//			}			try {				FileOutputStream fos = new FileOutputStream(file);				byte[] b = new byte[2048];				int j = 0;				while ((j = input.read(b)) != -1) {					fos.write(b, 0, j);				}				fos.flush();				fos.close();			} catch (FileNotFoundException e) {				// TODO Auto-generated catch block				e.printStackTrace();			} catch (IOException e) {				// TODO Auto-generated catch block				e.printStackTrace();			}		}else{			Log.i("tag", "NO SDCard.");		}	}		private String getMIMEType(File f){         String type="";        String fName=f.getName();        /* 取得扩展名 */        String end=fName.substring(fName.lastIndexOf(".")+1,fName.length()).toLowerCase();            /* 依扩展名的类型决定MimeType */      if(end.equals("pdf")){    	  type = "application/pdf";//      }      else if(end.equals("m4a")||end.equals("mp3")||end.equals("mid")||        end.equals("xmf")||end.equals("ogg")||end.equals("wav")){          type = "audio/*";         }        else if(end.equals("3gp")||end.equals("mp4")){          type = "video/*";        }        else if(end.equals("jpg")||end.equals("gif")||end.equals("png")||        end.equals("jpeg")||end.equals("bmp")){          type = "image/*";        }        else if(end.equals("apk")){           /* android.permission.INSTALL_PACKAGES */           type = "application/vnd.android.package-archive";       }//      else if(end.equals("pptx")||end.equals("ppt")){//    	  type = "application/vnd.ms-powerpoint"; //      }else if(end.equals("docx")||end.equals("doc")){//    	  type = "application/vnd.ms-word";//      }else if(end.equals("xlsx")||end.equals("xls")){//    	  type = "application/vnd.ms-excel";//      }      else{//    	  /*如果无法直接打开,就跳出软件列表给用户选择 */          type="*/*";      }      return type;    }   
[java]
  1. <SPAN style="FONT-FAMILY: Helvetica, Tahoma, Arial, sans-serif">转自:<A href="http://gundumw100.iteye.com/blog/1338645">http://gundumw100.iteye.com/blog/1338645</A>  
  2. </SPAN>  
转自:http://gundumw100.iteye.com/blog/1338645

转载地址:http://iezpi.baihongyu.com/

你可能感兴趣的文章
Linux开源系统对比Windows闭源系统的优势解析
查看>>
ls 命令详解
查看>>
关于浏览器内核你不得不了解的事
查看>>
Wire:Linux开源聊天应用
查看>>
百度、搜狗、讯飞同时宣布语音识别准确率达到97%,他们是怎么做到的?
查看>>
使用 Glyphr 玩转Linux字体
查看>>
aria2 让下载提速
查看>>
你玩过物联网操作系统吗?
查看>>
黑客需要身兼几种计算机语言?
查看>>
全新 Kali Linux 系统安装指南
查看>>
开源客户端框架:JavaScript
查看>>
你知道么?火狐搜集您的数据?
查看>>
从 ISO 镜像中提取和复制文件的绝招(Linux)
查看>>
大神教你如何构建面向应用的运维管理新思维
查看>>
总结四条对学习Linux系统有帮助的方法
查看>>
4 种方法识别Linux系统 USB 设备
查看>>
Linux 文件编码大挪移
查看>>
最最流行的10个开源数据可视化项目
查看>>
新人需要掌握的五大Linux终端命令的技巧
查看>>
超简单玩转 GitHub 的问题单(issue)
查看>>