摄像头拍照时,不要解析返回的data

看到《第一行代码》中调用摄像头拍照代码的如下:

@Override
public void onClick(View view) {
    if (btn_take_photo == view){
        File imgFile = new File(getExternalCacheDir(), "abc.png");
        //imgFile = "/storage/emulated/0/Android/data/com.lyl.avatar/cache/abc.png"
        if (imgFile.exists()){
            imgFile.delete();
        }
        try {
            imgFile.createNewFile();
        } catch (IOException e) {
            e.printStackTrace();
        }

        //File对象 -->  Uri对象
     if (Build.VERSION.SDK_INT >= 24){
            /*
                Android7.0以后不再使用真实路径的Uri,FileProvider是特殊的内容提供者,可以选择性的将封装过的Uri共享给外部
                FileProvider是ContentProvider的子类,清单文件中要添加provider
                imgUri的值打印出来为:"content://com.lyl.avatar.takephoto/my_imgs/Android/data/com.lyl.avatar/cache/abc.png"
            */
            imgUri = FileProvider.getUriForFile(MainActivity.this, "com.lyl.avatar.takephoto", imgFile);
        } else {
            //  imgUri的值打印出来为:"file:///storage/emulated/0/Android/data/com.lyl.avatar/cache/abc.png"
            imgUri = Uri.fromFile(imgFile);
        }

        Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        intent.putExtra(MediaStore.EXTRA_OUTPUT, imgUri);
        startActivityForResult(intent, TAKE_PHOTO_REQ);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if ((TAKE_PHOTO_REQ == requestCode) && (RESULT_OK == resultCode)){
        setImg(imgUri);
    }
}

public void setImg(Uri imgUri){
    //getContentResolver,内容解析器,和getContentResolver对应
    InputStream inputStream = null;
    try {
        inputStream = getContentResolver().openInputStream(imgUri);
        //BitmapFactory --> Bitmap
        Bitmap bitmap = BitmapFactory.decodeStream(inputStream);//bitmap : 位图对象
        iv_photo.setImageBitmap(bitmap);
    } catch (FileNotFoundException e) {
            e.printStackTrace();
    }
}

发现可以用getExternal的方式来获取uri,经尝试会报错,就搜索了下相关问题。
1).当指定uri时,即intent.putExtra(MediaStore.EXTRA_OUTPUT,imgUri); ,mSaveUri不为null,系统在保存完图片,直接setResult(RESULT_OK)了,并没有创建intent返回,故在onActivityResult中的data为null;

2).若不指定uri,mSaveUri为null会把图片转换为bitmap,创建Intent,把bitmap存放在data中,即在onActivityResult中通过 data.getExtras().get("data");就能拿到图片的Bitmap。但data返回的是缩略图,没有原始图片清晰。


故,在保存自己图片的uri时,不要使用解析返回的data的方法。若要使用返回的Intent类型的data,代码如下:

@Override
public void onClick(View view) {
    if (btn_take_photo == view){        
        Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        //intent.putExtra(MediaStore.EXTRA_OUTPUT, imgUri);//使mSaveUri为空
        startActivityForResult(intent, TAKE_PHOTO_REQ);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if ((TAKE_PHOTO_REQ == requestCode) && (RESULT_OK == resultCode)){
        try {
            Bitmap bitmap = (Bitmap) data.getExtras().get("data");
            iv_photo.setImageBitmap(bitmap);
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }
    }
}


参考链接:
解释 Android 调用系统相机,在onActivityResult中接收的data为null的原因

Android 调用系统相机返回data为null

getCacheDir()、getFilesDir()、getExternalFilesDir()、getExternalCacheDir()的作用

阅读更多
想对作者说点什么? 我来说一句

没有更多推荐了,返回首页