项目中使用到了文本文件下载的功能,该功能的实现可以使用okHttp来实现,结合项目的需求,代码如下:
public class DownfileUtils {
private static OkHttpClient okHttpClient = new OkHttpClient.Builder().connectTimeout(10000, TimeUnit.MILLISECONDS)
.readTimeout(10000, TimeUnit.MILLISECONDS)
.writeTimeout(10000, TimeUnit.MILLISECONDS).build();
private static String basePath = Environment.getExternalStorageDirectory().getAbsolutePath()
+ "/xxxx/xxxx" + "/xxxx/xxxx";//文件路径
private static String filePath;
//下载文件方法
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);
}
/**
* 下载文件
*/
public static void downReplyFile(String url, final ProgressBar progressBar, final String filename) {
DownfileUtils.downloadFile(url, new ProgressListener() {
@Override
public void onProgress(long currentBytes, long contentLength, boolean done) {
int progress = (int) (currentBytes * 100 / contentLength);
progressBar.setProgress(progress);//下载进度条
if (progress / 5 > 0) {
progressBar.setVisibility(View.VISIBLE);
progressBar.setProgress(progress);
}
if (progress == 100) {
progressBar.setVisibility(View.GONE);
}
}
}, new Callback() {
@Override
public void onFailure(Call call, IOException e) {
}
@Override
public void onResponse(Call call, Response response) throws IOException {
if (response != null) {
File file = new File(basePath);
if (!file.exists()) {
file.mkdir();
}
InputStream is = response.body().byteStream();
filePath = basePath + "/" + filename;
File downfile = new File(filePath);
if (downfile.isFile() && downfile.exists()) { //判断文件是否存在----存在则不处理
} else {
FileOutputStream fos = new FileOutputStream(downfile);//写文件
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();
}
}
}
});
}
public static String getBasePath() {
return basePath;
}
}
定义进度条的接口
public interface ProgressListener {
//已完成的 总的文件长度 是否完成
void onProgress(long currentBytes, long contentLength, boolean done);
}
请求响应类
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;
}
};
}
}
至此,下载功能代码展示完毕。