重命名应用程序在 android 10 中创建的 Mediastore 文件。正在处理 Android API 30 但在 API 29 中显示错误
Rename file of the Mediastore which is created by app in android 10. Working on Android API 30 but shows error in API 29
在这里,这个 renameFile(..) 函数在 Android API 30 中工作。但是,它在 Android API 29 中不起作用并显示错误如:
java.lang.IllegalArgumentException: 内容移动://media/external/file/116 不允许不属于明确定义的集合
更新-注:
---开始---
为了使用 sdk-29,我们必须使用 Uri 作为 extUri = MediaStore.Downloads.getContentUri(MediaStore.VOLUME_EXTERNAL) 像:
private static Uri extUri = MediaStore.Downloads.getContentUri(MediaStore.VOLUME_EXTERNAL);
代替下面的代码。并将 MediaStore.Files.FileColumns 更新为 MediaStore.Downloads
---结束---
Uri extUri = MediaStore.Files.getContentUri(MediaStore.VOLUME_EXTERNAL);
String relativeLocation = Environment.DIRECTORY_DOWNLOADS + File.separator + "AppFolder";
函数重命名文件(...)
boolean renameFile(Context context, String newName, String displayName) {
try {
Long id = getIdFromDisplayName(displayName);
ContentResolver contentResolver = context.getContentResolver();
Uri mUri = ContentUris.withAppendedId(extUri, id);
ContentValues contentValues = new ContentValues();
contentValues.put(MediaStore.Files.FileColumns.IS_PENDING, 1);
contentResolver.update(mUri, contentValues, null, null);
contentValues.clear();
contentValues.put(MediaStore.Files.FileColumns.DISPLAY_NAME, newName);
// contentValues.put(MediaStore.Files.FileColumns.MIME_TYPE, "files/pdf");
// contentValues.put(MediaStore.Files.FileColumns.RELATIVE_PATH, relativeLocation);
// contentValues.put(MediaStore.Files.FileColumns.TITLE, "SomeName");
// contentValues.put(MediaStore.Files.FileColumns.DATE_ADDED, System.currentTimeMillis() / 1000);
// contentValues.put(MediaStore.Files.FileColumns.DATE_TAKEN, System.currentTimeMillis());
contentValues.put(MediaStore.Files.FileColumns.IS_PENDING, 0);
contentResolver.update(mUri, contentValues, null, null);
return true;
} catch (Exception ex) {
ex.printStackTrace();
}
return false;
}
函数 getIdFromDisplayName(...)
@RequiresApi(api = Build.VERSION_CODES.Q)
Long getIdFromDisplayName(String displayName) {
String[] projection;
projection = new String[]{MediaStore.Files.FileColumns._ID};
// TODO This will break if we have no matching item in the MediaStore.
Cursor cursor = getContentResolver().query(extUri, projection,
MediaStore.Files.FileColumns.DISPLAY_NAME + " LIKE ?", new String[]{displayName}, null);
assert cursor != null;
cursor.moveToFirst();
if (cursor.getCount() > 0) {
int columnIndex = cursor.getColumnIndex(projection[0]);
long fileId = cursor.getLong(columnIndex);
cursor.close();
return fileId;
}
return null;
}
java.lang.IllegalArgumentException: Movement of content://media/external/file/116 which isn't part of well-defined collection not allowed
所以它是为了 Android 如果你使用 collection;
Q 不允许
Uri extUri = MediaStore.Files.getContentUri(MediaStore.VOLUME_EXTERNAL);
但是对于 'well-defined collection' 这样的
是允许的
Uri extUri = MediaStore.Images.Media.getContentUri(MediaStore.VOLUME_EXTERNAL);
// Use "Pictures/MyFolder" for RELATIVE_PATH
我留给你去寻找其他 well-defined collections.
为什么这只适用于 Android Q 我不知道。
您可以在 java 文件中看到消息:https://android.googlesource.com/platform/packages/providers/MediaProvider/+/refs/heads/master/src/com/android/providers/media/MediaProvider.java
引用:
// We only support movement under well-defined collections
switch (match) {
case AUDIO_MEDIA_ID:
case VIDEO_MEDIA_ID:
case IMAGES_MEDIA_ID:
case DOWNLOADS_ID:
break;
default:
throw new IllegalArgumentException("Movement of " + uri
+ " which isn't part of well-defined collection not allowed");
}
如果重命名失败,请使用 SAF(如前所述)。 How to rename a file in Android knowing only its media content Uri
我不得不自己面对重命名问题 (Android 29),上面的解决方案还不够。
这是因为我有一张物理 SD 卡,上面有
我想重命名的文件。
然后,指令:
extUri = MediaStore.Audio.Media.getContentUri(MediaStore.VOLUME_EXTERNAL);
没用;相反,我不得不:
列出“外部卷”(根据 Android 条款)
Set<String> lVls = MediaStore.getExternalVolumeNames(this);
..这给了我 2 卷:
"external_primary" (the built-in external storage)
"bc21-eafa" (the SD card external storage)
用第二个值初始化 'extUri',像这样:
extUri = MediaStore.Audio.Media.getContentUri("bc21-eafa");
应用本文中描述的其余过程。
感谢大家!
在这里,这个 renameFile(..) 函数在 Android API 30 中工作。但是,它在 Android API 29 中不起作用并显示错误如:
java.lang.IllegalArgumentException: 内容移动://media/external/file/116 不允许不属于明确定义的集合
更新-注:
---开始---
为了使用 sdk-29,我们必须使用 Uri 作为 extUri = MediaStore.Downloads.getContentUri(MediaStore.VOLUME_EXTERNAL) 像:
private static Uri extUri = MediaStore.Downloads.getContentUri(MediaStore.VOLUME_EXTERNAL);
代替下面的代码。并将 MediaStore.Files.FileColumns 更新为 MediaStore.Downloads
---结束---
Uri extUri = MediaStore.Files.getContentUri(MediaStore.VOLUME_EXTERNAL);
String relativeLocation = Environment.DIRECTORY_DOWNLOADS + File.separator + "AppFolder";
函数重命名文件(...)
boolean renameFile(Context context, String newName, String displayName) {
try {
Long id = getIdFromDisplayName(displayName);
ContentResolver contentResolver = context.getContentResolver();
Uri mUri = ContentUris.withAppendedId(extUri, id);
ContentValues contentValues = new ContentValues();
contentValues.put(MediaStore.Files.FileColumns.IS_PENDING, 1);
contentResolver.update(mUri, contentValues, null, null);
contentValues.clear();
contentValues.put(MediaStore.Files.FileColumns.DISPLAY_NAME, newName);
// contentValues.put(MediaStore.Files.FileColumns.MIME_TYPE, "files/pdf");
// contentValues.put(MediaStore.Files.FileColumns.RELATIVE_PATH, relativeLocation);
// contentValues.put(MediaStore.Files.FileColumns.TITLE, "SomeName");
// contentValues.put(MediaStore.Files.FileColumns.DATE_ADDED, System.currentTimeMillis() / 1000);
// contentValues.put(MediaStore.Files.FileColumns.DATE_TAKEN, System.currentTimeMillis());
contentValues.put(MediaStore.Files.FileColumns.IS_PENDING, 0);
contentResolver.update(mUri, contentValues, null, null);
return true;
} catch (Exception ex) {
ex.printStackTrace();
}
return false;
}
函数 getIdFromDisplayName(...)
@RequiresApi(api = Build.VERSION_CODES.Q)
Long getIdFromDisplayName(String displayName) {
String[] projection;
projection = new String[]{MediaStore.Files.FileColumns._ID};
// TODO This will break if we have no matching item in the MediaStore.
Cursor cursor = getContentResolver().query(extUri, projection,
MediaStore.Files.FileColumns.DISPLAY_NAME + " LIKE ?", new String[]{displayName}, null);
assert cursor != null;
cursor.moveToFirst();
if (cursor.getCount() > 0) {
int columnIndex = cursor.getColumnIndex(projection[0]);
long fileId = cursor.getLong(columnIndex);
cursor.close();
return fileId;
}
return null;
}
java.lang.IllegalArgumentException: Movement of content://media/external/file/116 which isn't part of well-defined collection not allowed
所以它是为了 Android 如果你使用 collection;
Q 不允许Uri extUri = MediaStore.Files.getContentUri(MediaStore.VOLUME_EXTERNAL);
但是对于 'well-defined collection' 这样的
是允许的Uri extUri = MediaStore.Images.Media.getContentUri(MediaStore.VOLUME_EXTERNAL);
// Use "Pictures/MyFolder" for RELATIVE_PATH
我留给你去寻找其他 well-defined collections.
为什么这只适用于 Android Q 我不知道。
您可以在 java 文件中看到消息:https://android.googlesource.com/platform/packages/providers/MediaProvider/+/refs/heads/master/src/com/android/providers/media/MediaProvider.java
引用:
// We only support movement under well-defined collections
switch (match) {
case AUDIO_MEDIA_ID:
case VIDEO_MEDIA_ID:
case IMAGES_MEDIA_ID:
case DOWNLOADS_ID:
break;
default:
throw new IllegalArgumentException("Movement of " + uri
+ " which isn't part of well-defined collection not allowed");
}
如果重命名失败,请使用 SAF(如前所述)。 How to rename a file in Android knowing only its media content Uri
我不得不自己面对重命名问题 (Android 29),上面的解决方案还不够。
这是因为我有一张物理 SD 卡,上面有 我想重命名的文件。
然后,指令:
extUri = MediaStore.Audio.Media.getContentUri(MediaStore.VOLUME_EXTERNAL);
没用;相反,我不得不:
列出“外部卷”(根据 Android 条款)
Set<String> lVls = MediaStore.getExternalVolumeNames(this);
..这给了我 2 卷:
"external_primary" (the built-in external storage) "bc21-eafa" (the SD card external storage)
用第二个值初始化 'extUri',像这样:
extUri = MediaStore.Audio.Media.getContentUri("bc21-eafa");
应用本文中描述的其余过程。 感谢大家!