70岁祝寿词,钟胜桢,cx252航班
okhttp是比较火的网络框架,它支持同步与异步请求,支持缓存,可以拦截,更方便下载大文件与上传文件的操作。下面我们用okhttp来下载文件并带进度条!
相关资料:
官网地址:
github源码地址:
一、服务器端简单搭建
可以参考搭建本地tomcat服务器及相关配置 这篇文章。
新建项目okhttpserver,在webcontent目录下新建downloadfile目录,将要下载的jpg文件放在项目下。如下图:
启动服务器,文件下载地址为http://localhost:8080/okhttpserver/download/2.jpg 。这样我们服务器就搭好了。
二、android端
下面我们进入正题。
1.build.gradle的dependencies配置如下
compile 'com.android.support:appcompat-v7:24.1.1' compile 'com.squareup.okhttp3:okhttp:3.2.0' compile 'com.squareup.okio:okio:1.7.0'
2.activity_main.xml
<?xml version="1.0" encoding="utf-8"?> <relativelayout 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: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.huang.myokhttp.mainactivity"> <button android:id="@+id/ok_download" android:layout_width="match_parent" android:layout_height="wrap_content" android:text="下载文件" /> <textview android:id="@+id/download_text" android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center" android:text="0" /> <progressbar android:id="@+id/download_progress" style="?android:attr/progressbarstylehorizontal" android:layout_width="match_parent" android:layout_height="wrap_content" android:max="100" /> </relativelayout>
3.编写okhttputil如下:
private static okhttpclient okhttpclient = new okhttpclient.builder().connecttimeout(10000, timeunit.milliseconds) .readtimeout(10000,timeunit.milliseconds) .writetimeout(10000,timeunit.milliseconds).build(); //下载文件方法 public static void downloadfile(string url, final progresslistener listener, callback callback){ //增加拦截器 okhttpclient client = okhttpclient.newbuilder().addnetworkinterceptor(new interceptor() { @override public response intercept(chain chain) throws ioexception { response response = chain.proceed(chain.request()); return response.newbuilder().body(new progressresponsebody(response.body(),listener)).build(); } }).build(); request request = new request.builder().url(url).build(); client.newcall(request).enqueue(callback); }
4.上面代码中的progressresponsebody是自己编写的类,progresslistener 是监听的接口:
progresslistener 接口
public interface progresslistener { //已完成的 总的文件长度 是否完成 void onprogress(long currentbytes, long contentlength, boolean done); }
progressresponsebody继承responsebody ,返回监听进度
public class progressresponsebody extends responsebody { public static final int update = 0x01; public static final string tag = progressresponsebody.class.getname(); private responsebody responsebody; private progresslistener mlistener; private bufferedsource bufferedsource; private handler myhandler; public progressresponsebody(responsebody body, progresslistener listener) { responsebody = body; mlistener = listener; if (myhandler==null){ myhandler = new myhandler(); } } /** * 将进度放到主线程中显示 */ class myhandler extends handler { public myhandler() { super(looper.getmainlooper()); } @override public void handlemessage(message msg) { switch (msg.what){ case update: progressmodel progressmodel = (progressmodel) msg.obj; //接口返回 if (mlistener!=null)mlistener.onprogress(progressmodel.getcurrentbytes(),progressmodel.getcontentlength(),progressmodel.isdone()); break; } } } @override public mediatype contenttype() { return responsebody.contenttype(); } @override public long contentlength() { return responsebody.contentlength(); } @override public bufferedsource source() { if (bufferedsource==null){ bufferedsource = okio.buffer(mysource(responsebody.source())); } return bufferedsource; } private source mysource(source source) { return new forwardingsource(source) { long totalbytesread = 0l; @override public long read(buffer sink, long bytecount) throws ioexception { long bytesread = super.read(sink, bytecount); totalbytesread +=bytesread!=-1?bytesread:0; //发送消息到主线程,progressmodel为自定义实体类 message msg = message.obtain(); msg.what = update; msg.obj = new progressmodel(totalbytesread,contentlength(),totalbytesread==contentlength()); myhandler.sendmessage(msg); return bytesread; } }; } }
5.mainactivity的代码:
public class mainactivity extends appcompatactivity implements view.onclicklistener{ public static final string tag = mainactivity.class.getname(); private progressbar download_progress; private textview download_text; public static string basepath = environment.getexternalstoragedirectory().getabsolutepath() + "/okhttp"; @override protected void oncreate(bundle savedinstancestate) { super.oncreate(savedinstancestate); setcontentview(r.layout.activity_main); download_progress = (progressbar) findviewbyid(r.id.download_progress); download_text = (textview) findviewbyid(r.id.download_text); findviewbyid(r.id.ok_download).setonclicklistener(this); } @override public void onclick(view view) { switch (view.getid()){ case r.id.ok_download: string url = "http://192.168.0.104:8080/okhttpserver/download/2.jpg"; final string filename = url.split("/")[url.split("/").length - 1]; log.i(tag, "filename==" + filename); okhttputil.downloadfile(url, new progresslistener() { @override public void onprogress(long currentbytes, long contentlength, boolean done) { log.i(tag, "currentbytes==" + currentbytes + "==contentlength==" + contentlength + "==done==" + done); int progress = (int) (currentbytes * 100 / contentlength); download_progress.setprogress(progress); download_text.settext(progress + "%"); } }, new callback() { @override public void onfailure(call call, ioexception e) { } @override public void onresponse(call call, response response) throws ioexception { if (response != null) { inputstream is = response.body().bytestream(); fileoutputstream fos = new fileoutputstream(new file(basepath + "/" + filename)); int len = 0; byte[] buffer = new byte[2048]; while (-1 != (len = is.read(buffer))) { fos.write(buffer, 0, len); } fos.flush(); fos.close(); is.close(); } } }); break; } } }
6.最后不要忘了添加权限:
<uses-permission android:name="android.permission.internet"/> <uses-permission android:name="android.permission.write_external_storage"/> <uses-permission android:name="android.permission.read_external_storage"/>
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持移动技术网。
如对本文有疑问,请在下面进行留言讨论,广大热心网友会与你互动!! 点击进行留言回复
Android studio开发小型对话机器人app(实例代码)
Android通过Java sdk的方式接入OpenCv的方法
Android 通过cmake的方式接入opencv的方法步骤
Android Studio finish()方法的使用与解决app点击“返回”(直接退出)
Android 进度条 ProgressBar的实现代码(隐藏、出现、加载进度)
网友评论