如何生成手机文档文件夹的正确URI?
测试设备:
1.小米M2102J20SI
2.模拟器Pixel 4 XL API 30
函数
askPermission()
打开目标目录。
@RequiresApi(Build.VERSION_CODES.Q)
private fun askPermission() {
val storageManager = application.getSystemService(Context.STORAGE_SERVICE) as StorageManager
val intent = storageManager.primaryStorageVolume.createOpenDocumentTreeIntent()
val targetDirectory = "WhatsApp%2FMedia%2F.Statuses"
var uri = intent.getParcelableExtra<Uri>("android.provider.extra.INITIAL_URI") as Uri
var scheme = uri.toString()
scheme = scheme.replace("/root/", "/document/")
scheme += "%3A$targetDirectory"
uri = Uri.parse(scheme)
intent.putExtra("android.provider.extra.INITIAL_URI", uri)
startActivityForResult(intent, REQUEST_CODE)
}
onActivityResult()
方法中将返回文件的Uri。
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (resultCode == RESULT_OK && requestCode == REQUEST_CODE) {
if (data != null) {
data.data?.let { treeUri ->
contentResolver.takePersistableUriPermission(
treeUri,
Intent.FLAG_GRANT_READ_URI_PERMISSION or
Intent.FLAG_GRANT_WRITE_URI_PERMISSION
)
readSDK30(treeUri)
}
}
}
}
readSDK30()
函数用于从 Uri
中读取文件和文件夹。
private fun readSDK30(treeUri: Uri) {
val tree = DocumentFile.fromTreeUri(this, treeUri)!!
thread {
val uriList = arrayListOf<Uri>()
listFiles(tree).forEach { uri ->
}
}
}
listFiles()
函数返回给定 Uri
中的所有文件和文件夹。
fun listFiles(folder: DocumentFile): List<Uri> {
return if (folder.isDirectory) {
folder.listFiles().mapNotNull { file ->
if (file.name != null) file.uri else null
}
} else {
emptyList()
}
}
EXTRA_INITIAL_URI
旨在成为您之前从ACTION_OPEN_DOCUMENT_TREE
获取的某些Uri
。 - CommonsWare