我正在使用下载管理器在android中下载文件。 但是在点击"取消"通知栏上的按钮,我无法收到任何广播。
我发现只有两个广播:
1。DownloadManager.ACTION_DOWNLOAD_COMPLETE
2。DownloadManager.ACTION_NOTIFICTION_CLICKED
下载管理员取消时是否有任何广播?如果没有那么请给我任何解决方案如何处理它?</ p>
答案 0 :(得分:0)
DownloadManager
在处理用户下载任务时会将信息写入数据库。因此,我们可以检查数据库的状态,以了解任务是否被取消。
DownloadManager
中的api,定期轮询状态将您的下载任务排入队列后,请启动以下线程进行检查。
private static class DownloadQueryThread extends Thread {
private static final String TAG = "DownloadQueryThread";
private final WeakReference<Context> context;
private DownloadManager downloadManager;
private final DownloadManager.Query downloadQuery;
private boolean shouldStopQuery = false;
private boolean downloadComplete = false;
private static final Object LOCK = new Object();
private final BroadcastReceiver downloadCompleteBroadcastReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
if (DownloadManager.ACTION_DOWNLOAD_COMPLETE.equals(intent.getAction())) {
synchronized (LOCK) {
shouldStopQuery = true;
downloadComplete = true;
}
}
}
};
/**
* Create from context and download id
* @param context the application context
* @param queryId the download id from {@link DownloadManager#enqueue(DownloadManager.Request)}
*/
public DownloadQueryThread(Context context, long queryId) {
this.context = new WeakReference<>(context);
this.downloadQuery = new DownloadManager.Query().setFilterById(queryId);
this.downloadManager = (DownloadManager) context.getSystemService(DOWNLOAD_SERVICE);
}
@Override
public void run() {
super.run();
if (context.get() != null) {
context.get().registerReceiver(downloadCompleteBroadcastReceiver,
new IntentFilter(DownloadManager.ACTION_DOWNLOAD_COMPLETE));
}
while (true) {
if (downloadManager != null) {
Cursor cursor = downloadManager.query(downloadQuery);
if (cursor != null && cursor.moveToFirst()) {
Log.d(TAG, "download running");
} else {
shouldStopQuery = true;
}
}
synchronized (LOCK) {
if (shouldStopQuery) {
if (downloadComplete) {
Log.d(TAG, "download complete");
} else {
Log.w(TAG, "download cancel");
}
break;
}
}
try {
sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
if (context.get() != null) {
context.get().unregisterReceiver(downloadCompleteBroadcastReceiver);
}
}
}
ContentObserver
在数据库更改时收到通知下载管理器的内容uri应为content://downloads/my_downloads
,我们可以监控此数据库的更改。当您使用下载ID开始下载时,将创建一行content://downloads/my_downloads/{downloadId}
。我们可以检查此光标以了解此任务是否被取消。如果返回的游标为空或null,则在数据库中找不到记录,则此下载任务将被用户取消。
// get the download id from DownloadManager#enqueue
getContentResolver().registerContentObserver(Uri.parse("content://downloads/my_downloads"),
true, new ContentObserver(null) {
@Override
public void onChange(boolean selfChange, Uri uri) {
super.onChange(selfChange, uri);
if (uri.toString().matches(".*\\d+$")) {
long changedId = Long.parseLong(uri.getLastPathSegment());
if (changedId == downloadId[0]) {
Log.d(TAG, "onChange: " + uri.toString() + " " + changedId + " " + downloadId[0]);
Cursor cursor = null;
try {
cursor = getContentResolver().query(uri, null, null, null, null);
if (cursor != null && cursor.moveToFirst()) {
Log.d(TAG, "onChange: running");
} else {
Log.w(TAG, "onChange: cancel");
}
} finally {
if (cursor != null) {
cursor.close();
}
}
}
}
}
});
答案 1 :(得分:0)
另一种解决方案是在下载目录中使用文件观察器
观察者声明:
private FileObserver fileObserver = new DownloadObserver(
Environment.getExternalStoragePublicDirectory(
Environment.DIRECTORY_DOWNLOADS ).getAbsolutePath(), this);
要开始时:
fileObserver.startWatching();
要停止时:
fileObserver.stopWatching();
观察者类:
public class DownloadObserver extends FileObserver {
public static final String TAG = "DownloadObserver";
Context context;
private static final int flags =
FileObserver.CLOSE_WRITE
| FileObserver.OPEN
| FileObserver.MODIFY
| FileObserver.DELETE
| FileObserver.MOVED_FROM;
public DownloadObserver(String path, Context context) {
super(path, flags);
this.context = context;
}
@Override
public void onEvent(int event, String path) {
if (path == null) {
return;
}
if (event == FileObserver.OPEN || event == FileObserver.CLOSE_WRITE) {
Log.d(TAG, "started or resumed: " + path);
} else if (event == FileObserver.DELETE) {
Log.e(TAG, "File delete:" + path);
//Here is your solution. Download was cancel from notification bar
} else {
//can be used to update download progress using DownloadManager.Query
}
}}