如何转换传递的Hierarchical URI额外数据?Android应用分享文件URI问题
解决Intent.EXTRA_STREAM对应的HierarchicalUri获取问题
遇到这种情况其实很常见——虽然你看到的是HierarchicalUri实例,但它本质是Uri的子类,所以我们只需要用正确的方式从Intent中取出并强转即可,不用纠结子类类型。下面给你两种可靠的获取方式,以及后续复制文件的步骤:
方式一:直接指定类型获取Parcelable
从Android 12(API 31)开始,getParcelableExtra支持传入具体的类型参数,这样能更安全地获取到Uri:Uri streamUri = getIntent().getParcelableExtra(Intent.EXTRA_STREAM, Uri.class);方式二:从Bundle中取出后强转
如果你的应用需要兼容更低版本,或者方式一没生效,可以直接从Intent的Extras中取出对象,再判断类型并强转:Bundle extras = getIntent().getExtras(); if (extras != null) { Object streamExtra = extras.get(Intent.EXTRA_STREAM); if (streamExtra instanceof Uri) { Uri streamUri = (Uri) streamExtra; // 拿到Uri后就可以处理文件了 } }
拿到Uri后复制文件的步骤
获取到Uri后,不能直接用文件路径操作,必须通过ContentResolver来访问内容:
if (streamUri != null) { try (InputStream inputStream = getContentResolver().openInputStream(streamUri)) { // 示例:将文件复制到应用内部存储 File targetFile = new File(getFilesDir(), "shared_content"); try (OutputStream outputStream = new FileOutputStream(targetFile)) { byte[] buffer = new byte[1024]; int bytesRead; while ((bytesRead = inputStream.read(buffer)) != -1) { outputStream.write(buffer, 0, bytesRead); } // 复制完成后的逻辑,比如通知用户 } } catch (IOException e) { e.printStackTrace(); // 处理异常,比如提示文件读取/写入失败 } }
注意事项
- 不用特意处理
HierarchicalUri的类型,因为它是Uri的实现类,强转完全安全; - Android 10及以上的Scoped Storage机制下,通过这种方式获取的Uri已经带有临时访问权限,不需要额外申请
READ_EXTERNAL_STORAGE权限; - 如果复制大文件,建议放在子线程中执行,避免阻塞主线程。
内容的提问来源于stack exchange,提问作者KeterDev
相关产品推荐
相关产品推荐

