package ml.puredark.hviewer.download;
import android.app.Service;
import android.content.Intent;
import android.graphics.Bitmap;
import android.net.Uri;
import android.os.Binder;
import android.os.Handler;
import android.os.IBinder;
import android.os.Looper;
import android.support.v4.provider.DocumentFile;
import android.text.TextUtils;
import android.webkit.JavascriptInterface;
import android.webkit.WebSettings;
import android.webkit.WebView;
import android.webkit.WebViewClient;
import com.facebook.common.references.CloseableReference;
import com.facebook.datasource.BaseDataSubscriber;
import com.facebook.datasource.DataSource;
import com.facebook.imagepipeline.memory.PooledByteBuffer;
import com.lzy.okgo.OkGo;
import com.lzy.okgo.request.GetRequest;
import com.lzy.okserver.download.DownloadInfo;
import com.lzy.okserver.listener.DownloadListener;
import com.umeng.analytics.MobclickAgent;
import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import ml.puredark.hviewer.HViewerApplication;
import ml.puredark.hviewer.R;
import ml.puredark.hviewer.beans.DownloadTask;
import ml.puredark.hviewer.beans.Picture;
import ml.puredark.hviewer.beans.Selector;
import ml.puredark.hviewer.beans.Site;
import ml.puredark.hviewer.beans.Video;
import ml.puredark.hviewer.core.RuleParser;
import ml.puredark.hviewer.dataholders.DownloadTaskHolder;
import ml.puredark.hviewer.helpers.FileHelper;
import ml.puredark.hviewer.helpers.Logger;
import ml.puredark.hviewer.http.HViewerHttpClient;
import ml.puredark.hviewer.http.ImageLoader;
import ml.puredark.hviewer.ui.fragments.SettingFragment;
import ml.puredark.hviewer.utils.FileType;
import ml.puredark.hviewer.utils.SharedPreferencesUtil;
import okhttp3.MediaType;
import okhttp3.Response;
import static android.webkit.WebSettings.LOAD_CACHE_ELSE_NETWORK;
import static ml.puredark.hviewer.HViewerApplication.mContext;
import static ml.puredark.hviewer.beans.DownloadItemStatus.STATUS_DOWNLOADED;
import static ml.puredark.hviewer.beans.DownloadItemStatus.STATUS_DOWNLOADING;
import static ml.puredark.hviewer.beans.DownloadItemStatus.STATUS_WAITING;
import static ml.puredark.hviewer.beans.DownloadTask.STATUS_COMPLETED;
import static ml.puredark.hviewer.beans.DownloadTask.STATUS_PAUSED;
/**
* Created by PureDark on 2016/8/16.
*/
public class DownloadService extends Service {
public static final String ACTION = "ml.puredark.hviewer.download.DownloadService";
public static final String ON_START = ".services.DownloadService.onStart";
public static final String ON_PAUSE = ".services.DownloadService.onPause";
public static final String ON_PROGRESS = ".services.DownloadService.onProgress";
public static final String ON_COMPLETE = ".services.DownloadService.onComplete";
public static final String ON_FAILURE = ".services.DownloadService.onFailure";
private DownloadBinder binder;
private DownloadTaskHolder holder = new DownloadTaskHolder(mContext);
private DownloadTask currTask;
// private BaseDownloadTask videoTask;
private DownloadInfo currInfo;
private com.lzy.okserver.download.DownloadManager downloadManager = com.lzy.okserver.download.DownloadService.getDownloadManager();
private String cachePath = mContext.getCacheDir().getAbsolutePath();
private Map<Integer, Picture> pictureInQueue;
public boolean downloadHighRes() {
return (boolean) SharedPreferencesUtil.getData(mContext,
SettingFragment.KEY_PREF_DOWNLOAD_HIGH_RES, false);
}
public void start(final DownloadTask task) {
pauseNoBrocast();
currTask = task;
currTask.status = DownloadTask.STATUS_GETTING;
if (task.collection.videos != null && task.collection.videos.size() > 0) {
//视频下载
downloadNewVideo(currTask);
} else {
//图片下载
pictureInQueue = new HashMap<>();
downloadNewPage(currTask);
downloadNewPage(currTask);
downloadNewPage(currTask);
}
Intent intent = new Intent(ON_START);
sendBroadcast(intent);
}
public void restart(final DownloadTask task) {
if (task.collection.videos != null && task.collection.videos.size() > 0) {
for (Video video : task.collection.videos) {
video.vlink = null;
video.percent = 0;
DownloadInfo downloadInfo = downloadManager.getDownloadInfo(video.content);
if (downloadInfo != null) {
downloadManager.pauseTask(downloadInfo.getTaskKey());
downloadManager.removeTask(downloadInfo.getTaskKey());
Logger.d("DownloadService", "removeTask");
}
}
}
start(task);
}
public void pause() {
if (currTask != null && currTask.status != STATUS_COMPLETED) {
currTask.status = STATUS_PAUSED;
if (currInfo != null) {
downloadManager.pauseTask(currInfo.getTaskKey());
currInfo = null;
}
if (currTask.collection.videos != null) {
for (Video video : currTask.collection.videos)
video.status = STATUS_WAITING;
}
holder.updateDownloadTasks(currTask);
currTask = null;
Intent intent = new Intent(ON_PAUSE);
sendBroadcast(intent);
}
}
private void pauseNoBrocast() {
if (currTask != null && currTask.status != STATUS_COMPLETED) {
currTask.status = STATUS_PAUSED;
if (currInfo != null) {
downloadManager.pauseTask(currInfo.getTaskKey());
currInfo = null;
}
if (currTask.collection.videos != null) {
for (Video video : currTask.collection.videos)
video.status = STATUS_WAITING;
}
holder.updateDownloadTasks(currTask);
currTask = null;
}
}
public void stop() {
pauseNoBrocast();
currTask = null;
if (currInfo != null) {
downloadManager.pauseTask(currInfo.getTaskKey());
downloadManager.removeTask(currInfo.getTaskKey());
currInfo = null;
}
}
public DownloadTask getCurrTask() {
return currTask;
}
private void downloadNewVideo(final DownloadTask task) {
boolean isCompleted = true;
Video currVideo = null;
for (Video video : task.collection.videos) {
if (video.vlink != null && (video.vlink.startsWith("file://") || video.vlink.startsWith("content://"))) {
video.status = STATUS_DOWNLOADED;
}
if (video.status == STATUS_WAITING) {
video.status = STATUS_DOWNLOADING;
currVideo = video;
isCompleted = false;
break;
} else if (video.status == STATUS_DOWNLOADING) {
isCompleted = false;
}
}
Logger.d("DownloadService", "downloadNewVideo: isCompleted = " + isCompleted);
if (currVideo == null) {
if (isCompleted) {
task.status = STATUS_COMPLETED;
Calendar calendar = Calendar.getInstance();
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm");
task.collection.datetime = dateFormat.format(calendar.getTime());
task.collection.gid = 0;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_COMPLETE);
sendBroadcast(intent);
// 统计下载完成次数
MobclickAgent.onEvent(mContext, "DownloadTaskCompleted");
// 记录信息,以求恢复删除了的下载记录
String rootPath = task.path.substring(0, task.path.lastIndexOf("/"));
String dirName = task.path.substring(task.path.lastIndexOf("/") + 1, task.path.length());
FileHelper.createFileIfNotExist("detail.txt", rootPath, dirName);
FileHelper.writeString(HViewerApplication.getGson().toJson(task), "detail.txt", rootPath, dirName);
}
return;
}
Logger.d("DownloadService", "downloadNewVideo: isCompleted2 = " + isCompleted);
if (!TextUtils.isEmpty(currVideo.vlink)) {
currVideo.retries = 0;
loadVideo(currVideo, task);
} else {
getVideoUrl(currVideo, task);
}
}
private void getVideoUrl(final Video video, final DownloadTask task) {
Logger.d("DownloadService", "getVideoUrl: video.content = " + video.content);
new Thread(() -> {
Response response = HViewerHttpClient.getResponseHeader(video.content, task.collection.site.getHeaders());
if (response == null) {
task.status = STATUS_PAUSED;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "视频地址获取失败,请检查网络连接");
sendBroadcast(intent);
return;
}
MediaType contentType = response.body().contentType();
String finalUrl = response.request().url().toString();
Logger.d("DownloadService", "contentType = " + contentType.toString());
Logger.d("DownloadService", "finalUrl = " + finalUrl);
if (contentType.type().equals("video")) {
video.vlink = finalUrl;
Logger.d("DownloadService", "realUrl=" + video.vlink);
video.retries = 0;
loadVideo(video, task);
} else {
HViewerHttpClient.get(video.content, task.collection.site.getHeaders(), new HViewerHttpClient.OnResponseListener() {
@Override
public void onSuccess(String contentType, Object result) {
if (result == null || result.equals("") || !(result instanceof String)) {
onFailure(null);
} else {
String html = (String) result;
List<String> videoUrls = RuleParser.getVideoUrl(html, video.content);
if (videoUrls.size() <= 0) {
onFailure(null);
} else {
new Thread(() -> {
String realUrl = null;
if (videoUrls.size() == 1) {
realUrl = videoUrls.get(0);
Logger.d("DownloadService", "videoUrl=" + videoUrls.get(0));
} else {
long maxSize = 0;
for (String videoUrl : videoUrls) {
Logger.d("DownloadService", "videoUrl=" + videoUrl);
long size = HViewerHttpClient.getContentLength(videoUrl, task.collection.site.getHeaders());
if (size == 0)
continue;
if (size > maxSize) {
maxSize = size;
realUrl = videoUrl;
}
Logger.d("DownloadService", "size=" + size);
}
}
if (realUrl == null) {
onFailure(null);
return;
}
video.vlink = realUrl;
Logger.d("DownloadService", "realUrl=" + realUrl);
video.retries = 0;
loadVideo(video, task);
}).start();
}
}
}
@Override
public void onFailure(HViewerHttpClient.HttpError error) {
task.status = STATUS_PAUSED;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "视频地址获取失败,请检查网络连接");
Logger.d("DownloadService", "video.content : " + video.content);
sendBroadcast(intent);
}
});
}
}).start();
}
private void loadVideo(final Video video, final DownloadTask task) {
Logger.d("DownloadService", "loadVideo: video.vlink=" + video.vlink);
downloadManager.pauseAllTask();
DownloadInfo downloadInfo = downloadManager.getDownloadInfo(video.content);
if (downloadInfo != null) {
Logger.d("DownloadService", "loadVideo: startExisted : ");
downloadManager.addTask(downloadInfo.getTaskKey(), downloadInfo.getRequest(), downloadInfo.getListener());
currInfo = downloadInfo;
} else {
Logger.d("DownloadService", "loadVideo: addNew");
String dirName = DownloadManager.generateDirName(task.collection, 0);
int i = 2;
while (FileHelper.isFileExist(dirName, cachePath)) {
dirName = DownloadManager.generateDirName(task.collection, i++);
}
downloadManager.setTargetFolder(cachePath + "/" + dirName);
GetRequest request = OkGo.get(video.vlink);
downloadManager.addTask(video.content, request, new DownloadListener() {
@Override
public void onProgress(DownloadInfo downloadInfo) {
long currentSize = downloadInfo.getDownloadLength();
float progress = downloadInfo.getProgress();
Logger.d("DownloadService", "onProgress: currentSize=" + currentSize);
Logger.d("DownloadService", "onProgress: progress=" + progress);
Logger.d("DownloadService", "onProgress: video.status=" + video.status);
video.percent = Math.round(progress * 100);
Intent intent = new Intent(ON_PROGRESS);
sendBroadcast(intent);
}
@Override
public void onFinish(DownloadInfo downloadInfo) {
new Thread(() -> {
long currentSize = downloadInfo.getDownloadLength();
Logger.d("DownloadService", "onFinish: currentSize=" + currentSize);
Logger.d("DownloadService", "onFinish: targetPath=" + downloadInfo.getTargetPath());
saveVideo(video, task, Uri.parse(downloadInfo.getTargetPath()));
Intent intent = new Intent(ON_PROGRESS);
sendBroadcast(intent);
if (task.status != STATUS_PAUSED && task.status != STATUS_COMPLETED) {
downloadNewVideo(task);
}
}).start();
}
@Override
public void onError(DownloadInfo downloadInfo, String errorMsg, Exception e) {
if (video.retries < 15) {
int delay = 1000 * video.retries;
video.retries++;
video.status = STATUS_DOWNLOADING;
new Handler().postDelayed(() -> loadVideo(video, task), delay);
} else {
video.retries = 0;
task.status = STATUS_PAUSED;
video.status = STATUS_WAITING;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", errorMsg);
Logger.d("DownloadService", "video.content : " + video.content);
sendBroadcast(intent);
}
}
});
currInfo = downloadManager.getDownloadInfo(video.vlink);
}
}
private void saveVideo(Video video, DownloadTask task, Uri uri) {
DocumentFile documentFile;
File file = new File(uri.getPath());
String fileName = getFileName(video.vid, task.collection.videos.size());
String postfix = "mp4";
fileName += "." + postfix;
String rootPath = task.path.substring(0, task.path.lastIndexOf("/"));
String dirName = task.path.substring(task.path.lastIndexOf("/") + 1, task.path.length());
documentFile = FileHelper.createFileIfNotExist(fileName, rootPath, dirName);
Logger.d("DownloadService", "saveVideo : documentFile : " + documentFile);
if (documentFile == null || !FileHelper.writeFromFile(file, documentFile)) {
task.status = STATUS_PAUSED;
video.status = STATUS_WAITING;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "保存失败,请重新设置下载目录");
sendBroadcast(intent);
return;
}
Logger.d("DownloadService", "saveVideo : done : " + documentFile.getUri().toString());
video.vlink = documentFile.getUri().toString();
video.status = STATUS_DOWNLOADED;
holder.updateDownloadTasks(task);
}
private void downloadNewPage(final DownloadTask task) {
if (task.collection.pictures == null) {
task.status = STATUS_PAUSED;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "图册中不含有任何图片");
sendBroadcast(intent);
return;
}
boolean isCompleted = true;
Picture currPic = null;
for (Picture picture : task.collection.pictures) {
if (picture.status == STATUS_WAITING) {
currPic = picture;
currPic.status = STATUS_DOWNLOADING;
isCompleted = false;
break;
} else if (picture.status == STATUS_DOWNLOADING) {
isCompleted = false;
}
}
if (currPic == null) {
if (isCompleted) {
task.status = STATUS_COMPLETED;
Calendar calendar = Calendar.getInstance();
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm");
task.collection.datetime = dateFormat.format(calendar.getTime());
task.collection.gid = 0;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_COMPLETE);
sendBroadcast(intent);
// 统计下载完成次数
MobclickAgent.onEvent(mContext, "DownloadTaskCompleted");
// 记录信息,以求恢复删除了的下载记录
String rootPath = task.path.substring(0, task.path.lastIndexOf("/"));
String dirName = task.path.substring(task.path.lastIndexOf("/") + 1, task.path.length());
FileHelper.createFileIfNotExist("detail.txt", rootPath, dirName);
FileHelper.writeString(HViewerApplication.getGson().toJson(task), "detail.txt", rootPath, dirName);
}
return;
}
final Picture picture = currPic;
boolean highRes = downloadHighRes();
if (!TextUtils.isEmpty(picture.highRes) && highRes) {
picture.retries = 0;
loadPicture(picture, task, true);
} else if (!TextUtils.isEmpty(picture.pic) && !highRes) {
picture.retries = 0;
loadPicture(picture, task, false);
} else if (task.collection.site.hasFlag(Site.FLAG_SINGLE_PAGE_BIG_PICTURE)
&& task.collection.site.extraRule != null) {
if (task.collection.site.extraRule.pictureRule != null && task.collection.site.extraRule.pictureRule.url != null)
getPictureUrl(picture, task, task.collection.site.extraRule.pictureRule.url, task.collection.site.extraRule.pictureRule.highRes);
else if (task.collection.site.extraRule.pictureUrl != null)
getPictureUrl(picture, task, task.collection.site.extraRule.pictureUrl, task.collection.site.extraRule.pictureHighRes);
} else if (task.collection.site.picUrlSelector != null) {
getPictureUrl(picture, task, task.collection.site.picUrlSelector, null);
} else {
picture.pic = picture.url;
picture.retries = 0;
loadPicture(picture, task, false);
}
}
private void getPictureUrl(final Picture picture, final DownloadTask task, final Selector selector, final Selector highResSelector) {
Logger.d("DownloadService", picture.url);
if (Picture.hasPicPosfix(picture.url)) {
picture.pic = picture.url;
loadPicture(picture, task, false);
} else
//如果需要执行JS才能获取完整数据,则不得不使用webView来载入页面
if (task.collection.site.hasFlag(Site.FLAG_JS_NEEDED_ALL)) {
new Handler(Looper.getMainLooper()).post(() -> {
WebView webView = new WebView(mContext);
WebSettings mWebSettings = webView.getSettings();
mWebSettings.setJavaScriptEnabled(true);
mWebSettings.setBlockNetworkImage(true);
mWebSettings.setDomStorageEnabled(true);
mWebSettings.setUserAgentString(getResources().getString(R.string.UA));
mWebSettings.setCacheMode(LOAD_CACHE_ELSE_NETWORK);
webView.addJavascriptInterface(this, "HtmlParser");
webView.setWebViewClient(new WebViewClient() {
@Override
public void onPageFinished(WebView view, String url) {
//Load HTML
pictureInQueue.put(picture.pid, picture);
boolean extra = !selector.equals(task.collection.site.picUrlSelector);
webView.loadUrl("javascript:window.HtmlParser.onResultGot(document.documentElement.outerHTML, " + picture.pid + ", " + extra + ");");
Logger.d("DownloadService", "onPageFinished");
}
});
webView.loadUrl(picture.url);
new Handler().postDelayed(() -> webView.stopLoading(), 30000);
});
Logger.d("DownloadService", "WebView");
} else
HViewerHttpClient.get(picture.url, task.collection.site.getHeaders(), new HViewerHttpClient.OnResponseListener() {
@Override
public void onSuccess(String contentType, Object result) {
if (result == null || result.equals("")) {
onFailure(null);
} else if (contentType.contains("image")) {
picture.pic = picture.url;
if (result instanceof Bitmap)
savePicture(picture, task, result);
else
loadPicture(picture, task, false);
} else {
picture.pic = RuleParser.getPictureUrl((String) result, selector, picture.url);
picture.highRes = RuleParser.getPictureUrl((String) result, highResSelector, picture.url);
if (!TextUtils.isEmpty(picture.highRes) && downloadHighRes()) {
picture.retries = 0;
picture.referer = picture.url;
loadPicture(picture, task, true);
} else if (!TextUtils.isEmpty(picture.pic)) {
picture.retries = 0;
picture.referer = picture.url;
loadPicture(picture, task, false);
} else {
onFailure(null);
}
}
}
@Override
public void onFailure(HViewerHttpClient.HttpError error) {
task.status = STATUS_PAUSED;
picture.status = STATUS_WAITING;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "图片地址获取失败,请检查网络连接");
Logger.d("DownloadService", "picture.url : " + picture.url);
sendBroadcast(intent);
}
});
}
@JavascriptInterface
public void onResultGot(String html, int pid, boolean extra) {
Picture picture = pictureInQueue.get(pid);
if (picture == null)
return;
pictureInQueue.remove(pid);
Selector selector = (extra) ? currTask.collection.site.extraRule.pictureUrl : currTask.collection.site.picUrlSelector;
Selector highResSelector = (extra) ? currTask.collection.site.extraRule.pictureHighRes : null;
picture.pic = RuleParser.getPictureUrl(html, selector, picture.url);
picture.highRes = RuleParser.getPictureUrl(html, highResSelector, picture.url);
if (!TextUtils.isEmpty(picture.highRes) && downloadHighRes()) {
picture.retries = 0;
picture.referer = picture.url;
loadPicture(picture, currTask, true);
} else if (!TextUtils.isEmpty(picture.pic)) {
picture.retries = 0;
picture.referer = picture.url;
loadPicture(picture, currTask, false);
} else {
currTask.status = STATUS_PAUSED;
picture.status = STATUS_WAITING;
holder.updateDownloadTasks(currTask);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "图片地址获取失败,请检查网络连接");
Logger.d("DownloadService", "apiUrl : " + picture.url);
sendBroadcast(intent);
}
}
private void loadPicture(final Picture picture, final DownloadTask task, final boolean highRes) {
String url = (highRes) ? picture.highRes : picture.pic;
Logger.d("DownloadService", "loadPicture pic : " + picture.pic);
Logger.d("DownloadService", "loadPicture highRes : " + picture.highRes);
Logger.d("DownloadService", "loadPicture apiUrl : " + url);
ImageLoader.loadResourceFromUrl(getApplicationContext(), url, task.collection.site.cookie, picture.referer,
new BaseDataSubscriber<CloseableReference<PooledByteBuffer>>() {
private DownloadTask myTask = task;
@Override
protected void onNewResultImpl(DataSource<CloseableReference<PooledByteBuffer>> dataSource) {
if (!dataSource.isFinished()) {
return;
}
CloseableReference<PooledByteBuffer> ref = dataSource.getResult();
if (ref != null) {
try {
PooledByteBuffer imageBuffer = ref.get();
savePicture(picture, myTask, imageBuffer);
} finally {
CloseableReference.closeSafely(ref);
}
}
}
@Override
protected void onFailureImpl(DataSource<CloseableReference<PooledByteBuffer>> dataSource) {
if (picture.retries < 15) {
int delay = 1000 * picture.retries;
picture.retries++;
picture.status = STATUS_DOWNLOADING;
new Handler().postDelayed(() -> loadPicture(picture, task, highRes), delay);
} else {
picture.retries = 0;
task.status = STATUS_PAUSED;
picture.status = STATUS_WAITING;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "图片下载失败,也许您需要代理");
sendBroadcast(intent);
}
}
});
}
private void savePicture(Picture picture, DownloadTask task, Object pic) {
try {
DocumentFile documentFile;
if (pic instanceof Bitmap) {
String fileName = getFileName(picture.pid, task.collection.pictures.size());
fileName += ".jpg";
String rootPath = task.path.substring(0, task.path.lastIndexOf("/"));
String dirName = task.path.substring(task.path.lastIndexOf("/") + 1, task.path.length());
documentFile = FileHelper.createFileIfNotExist(fileName, rootPath, dirName);
FileHelper.saveBitmapToFile((Bitmap) pic, documentFile);
} else if (pic instanceof PooledByteBuffer) {
PooledByteBuffer buffer = (PooledByteBuffer) pic;
byte[] bytes = new byte[buffer.size()];
buffer.read(0, bytes, 0, buffer.size());
String fileName = getFileName(picture.pid, task.collection.pictures.size());
String postfix = FileType.getFileType(bytes, FileType.TYPE_IMAGE);
fileName += "." + postfix;
String rootPath = task.path.substring(0, task.path.lastIndexOf("/"));
String dirName = task.path.substring(task.path.lastIndexOf("/") + 1, task.path.length());
documentFile = FileHelper.createFileIfNotExist(fileName, rootPath, dirName);
if (!FileHelper.writeBytes(bytes, documentFile)) {
throw new IOException();
}
} else
return;
if (documentFile == null)
return;
if (picture.pid == 1) {
task.collection.cover = documentFile.getUri().toString();
}
picture.thumbnail = documentFile.getUri().toString();
picture.pic = documentFile.getUri().toString();
picture.retries = 0;
picture.status = STATUS_DOWNLOADED;
Intent intent = new Intent(ON_PROGRESS);
sendBroadcast(intent);
if (task.status != STATUS_PAUSED && task.status != STATUS_COMPLETED) {
downloadNewPage(task);
}
//Log.d("DownloadManager", "picture.pid = " + picture.pid);
} catch (IOException e) {
e.printStackTrace();
task.status = STATUS_PAUSED;
picture.status = STATUS_WAITING;
holder.updateDownloadTasks(task);
Intent intent = new Intent(ON_FAILURE);
intent.putExtra("message", "保存失败,请重新设置下载目录");
sendBroadcast(intent);
} catch (OutOfMemoryError error) {
// 这里就算OOM了,就当作下载失败,不影响程序继续运行
}
}
private String getFileName(int id, int size) {
String fileName;
if (size >= 1000) {
fileName = String.format("%04d", id);
} else if (size >= 100) {
fileName = String.format("%03d", id);
} else if (size >= 10) {
fileName = String.format("%02d", id);
} else {
fileName = id + "";
}
return fileName;
}
@Override
public IBinder onBind(Intent intent) {
if (binder == null)
binder = new DownloadBinder();
return binder;
}
@Override
public void onCreate() {
super.onCreate();
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
return super.onStartCommand(intent, flags, startId);
}
@Override
public void onDestroy() {
super.onDestroy();
pause();
}
public class DownloadBinder extends Binder {
public void start(DownloadTask task) {
DownloadService.this.start(task);
}
public void restart(DownloadTask task) {
DownloadService.this.restart(task);
}
public void pause() {
DownloadService.this.pause();
}
public void stop() {
DownloadService.this.stop();
}
public DownloadTask getCurrTask() {
return DownloadService.this.getCurrTask();
}
}
}