已下载视频无法播放求助:DownloadManager获取Uri为空
Hey there, let's break down why you're getting a null Uri when trying to access your downloaded video, and fix it step by step:
1. First, Verify the Download Actually Completed
The most common reason for a null Uri is that the download task didn't finish successfully. getUriForDownloadedFile() will return null if the download is still in progress, failed, or was canceled.
Add this check before trying to get the Uri to confirm the status:
DownloadManager downloadManager = (DownloadManager) getSystemService(Context.DOWNLOAD_SERVICE); DownloadManager.Query query = new DownloadManager.Query().setFilterById(reference); Cursor cursor = downloadManager.query(query); if (cursor.moveToFirst()) { int status = cursor.getInt(cursor.getColumnIndex(DownloadManager.COLUMN_STATUS)); if (status != DownloadManager.STATUS_SUCCESSFUL) { // Handle failed/incomplete download int reason = cursor.getInt(cursor.getColumnIndex(DownloadManager.COLUMN_REASON)); Log.e("DownloadIssue", "Download failed with status: " + status + ", reason: " + reason); cursor.close(); return; } } else { // No record found for this download reference Log.e("DownloadIssue", "No download record found for reference ID: " + reference); cursor.close(); return; } cursor.close(); // Now try getting the Uri Uri uri = downloadManager.getUriForDownloadedFile(reference);
2. Check Scoped Storage Permissions (Android 10+)
Starting with Android 10 (API 29), Scoped Storage restricts access to external files. If you downloaded the video to a public external directory (like Downloads), you might run into permission issues:
- For API 30+: You need to request the
MANAGE_EXTERNAL_STORAGEpermission (note this is a special permission that requires user approval via settings). - For API 29: You can temporarily enable legacy storage by adding
android:requestLegacyExternalStorage="true"to your<application>tag inAndroidManifest.xml(though this is not recommended for long-term use).
A better alternative is to download the file to your app's private external directory using setDestinationInExternalFilesDir() when creating your DownloadManager.Request—this avoids most permission headaches:
DownloadManager.Request request = new DownloadManager.Request(Uri.parse(yourVideoUrl)); request.setDestinationInExternalFilesDir(this, Environment.DIRECTORY_MOVIES, "your_video.mp4");
3. Ensure Your Download Reference ID is Valid
Double-check that the reference variable you're passing is the exact ID returned by downloadManager.enqueue(request). Common mistakes here include:
- Accidentally overwriting the
referencevalue with an invalid number. - Storing the ID as an
intinstead of along(since download IDs are 64-bit values, which can overflow an int). - Saving/retrieving the ID incorrectly (e.g., using SharedPreferences and mixing up data types).
4. Confirm the Downloaded File Still Exists
It's possible the file was deleted or moved after download (by the user, a cleanup app, or system). You can check its existence using the local file path from the DownloadManager cursor:
String localUriString = cursor.getString(cursor.getColumnIndex(DownloadManager.COLUMN_LOCAL_URI)); File downloadedFile = new File(Uri.parse(localUriString).getPath()); if (!downloadedFile.exists()) { Log.e("FileMissing", "Downloaded file no longer exists at: " + downloadedFile.getAbsolutePath()); }
Once you've ruled out these issues, your Uri should load correctly into VideoView.
内容的提问来源于stack exchange,提问作者Naman Jain

