Android中Uri 和Path之间的相互转化

Android Uri to Path

现在遇到的常规Uri有两种:

  • 媒体文件的Uri是content://, 表示这是一个数据库数据。去数据库查询正常返回。
  • 其他的文件Uri是file://, 表示这个是一个文件。这个uri是通过Uri.fromFile(File file)方法生成。

Media Uri To Path

在我简书中有一篇文章Android Uri to Path当中介绍了如何把从相册返回的Uri转换为Media Uri,然后再通过获得的Media Uri获取图片的Path。最终通过BitmapFractory创建相应的Bitmap对象。

File Uri To Path

这个转换相对比较简单,我们可以直接利用Android SDK提供的Uri.getPath()方法来获取相应的路径,然后利用Java IO来获取输入流,创建Bitmap。如果想直接通过File Uri获取输入流,我们可以通过调用ContentResolves.openInputStream(Uri uri)返回得到输入流。

bitmap = BitmapFactory.decodeStream(
                    getContentResolver().openInputStream(
                            GetImageUri.getImageStreamFromExternal("Screenshots/Screenshot.png"))
            );

这里的GetImageUri.getImageStreamFromExternal是我自己写的一个工具类:


public static Uri getImageStreamFromExternal(String imageName) {
        File externalPubPath = Environment.getExternalStoragePublicDirectory(
                Environment.DIRECTORY_PICTURES
        );

        File picPath = new File(externalPubPath, imageName);
        Uri uri = null;
        if(picPath.exists()) {
             uri = Uri.fromFile(picPath);
        }

        return uri;
    }

通过该静态方法可以将外部存储路径下的Pictures目录下的文件的路径转换为File Uri。

Android Path To Uri

File Path To File Uri

直接上代码:

public static Uri getImageStreamFromExternal(String imageName) {
        File externalPubPath = Environment.getExternalStoragePublicDirectory(
                Environment.DIRECTORY_PICTURES
        );

        File picPath = new File(externalPubPath, imageName);
        Uri uri = null;
        if(picPath.exists()) {
             uri = Uri.fromFile(picPath);
        }

        return uri;
    }

这里我们看到,最核心的部分就是利用Uri.fromFile()方法获取到指定路径的File Uri。

File Path To Media Uri

直接上代码:

public static Uri getMediaUriFromPath(Context context, String path) {
        Uri mediaUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
        Cursor cursor = context.getContentResolver().query(mediaUri,
                null,
                MediaStore.Images.Media.DISPLAY_NAME + "= ?",
                new String[] {path.substring(path.lastIndexOf("/") + 1)},
                null);

        Uri uri = null;
        if(cursor.moveToFirst()) {
            uri = ContentUris.withAppendedId(mediaUri,
                    cursor.getLong(cursor.getColumnIndex(MediaStore.Images.Media._ID)));
        }
        cursor.close();
        return uri;
    }

代码分析:首先我们获取到相册数据库表的Uri,mediaUri。然后我们利用ContentResolver.query()方法,并且selectionArgs传入根据指定路径获得的文件名来得到一个cursor对象。然后通过这个cursor对象我们获取到指定文件的ID。最后通过ContentUri组合mediaUri和图片的Id,得到最终的Media Uri。

MediaStore

这个类很重要,官方文档介绍:The Media provider contains meta data for all available media on both internal and external storage devices.意思大概是该类包含了所有在设备的内部存储和外部存储的媒体文件的元数据。例如通过指定MediaStore.ACTION_IMAGE_CAPTURE为action的Intent可以打开系统相机,MediaStore.EXTRA_OUTPUT是指定存储Uri的键...

渣渣英语翻译,见谅...总之这个类在访问媒体文件时很重要。

还有一些对应数据库表列名,android.provider.MediaStore.MediaColumns中DATA指的是文件路径,DISPLAY_NAME代表文件名...还有android.provider.BaseColumns中_ID就是媒体文件的ID。有需要用到时,可以查阅文档。

参考

Android File Uri的转换path

[Android] URI那些事



作者:FoolishDev
链接:https://www.jianshu.com/p/33bc363290e9
來源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
  • 6
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值