如何在 Android 中插入带有内容解析器的文件?

How do insert file with content resolver in Android?

我正在尝试将音频文件插入 Android 中的共享存储。我在 api 29(模拟器)上遇到错误。

错误:

java.lang.IllegalArgumentException: Primary directory (invalid) not allowed for content://media/external_primary/audio/media; allowed directories are [Alarms, Music, Notifications, Podcasts, Ringtones]

我的密码是:

...
Uri collection = (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) 
                ? MediaStore.Audio.Media.getContentUri(MediaStore.VOLUME_EXTERNAL_PRIMARY)
                : MediaStore.Audio.Media.getContentUri(MediaStore.VOLUME_EXTERNAL);

values = new ContentValues();
values.put(MediaStore.Audio.Media.DISPLAY_NAME, targetFileName);
values.put(MediaStore.Audio.Media.RELATIVE_PATH, targetFileDirPath);
values.put(MediaStore.Audio.Media.MIME_TYPE, "audio/mpeg");
values.put(MediaStore.Audio.Media.IS_PENDING, 1);

resolver = getContentResolver();
uri = resolver.insert(collection, values); // error throws from here
outputStream = uri != null ? resolver.openOutputStream(uri) : null;
...

这个错误的原因是什么,我该如何解决这个问题?

显然,MediaStore.Audio.Media.getContentUri() 不是 return 可直接使用的 Uri,至少在 Android 10+ 上是这样。它指向“音频”的抽象位置,但您不能直接向该位置写入内容 Uri。相反,您需要使用 RELATIVE_PATH 来指定支持的集合之一(AlarmsMusicNotificationsPodcastsRingtones),然后是你想要的任何路径。

请注意,RELATIVE_PATH 本身是 Android 10 的新功能。对于 Android 9 和更旧的设备,我建议直接写入文件系统。

{ 确认使用@CommnWare

values.put(MediaStore.MediaColumns.RELATIVE_PATH, Environment.DIRECTORY_DOWNLOADS + "/" + FILE_DIR); values.put(MediaStore.MediaColumns.IS_PENDING, 1); values.put(MediaStore.MediaColumns.DISPLAY_NAME, FILE_NAME); values.put(MediaStore.MediaColumns.MIME_TYPE, "text/plain");enter code here

ContentResolver 解析器 = _context.getContentResolver(); resolver.insert(MediaStore.Files.getContentUri(MediaStore.VOLUME_EXTERNAL_PRIMARY), 值); }