You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

API 33+ 相机拍照后触发java.lang.NullPointerException: uri异常求助

解决拍照后因Uri空指针崩溃的问题

问题分析

应用拍照功能完成后崩溃,报错java.lang.NullPointerException: uri,堆栈显示错误发生在HomeActivity.onActivityResult调用ContentResolver.openInputStream时。图库功能正常,问题出在拍照流程的Uri处理上:

  • 当通过intent.putExtra("output", uri)指定相机输出路径后,相机不会将Uri放入返回的Intent(data)中,若代码尝试从data里提取Uri,必然得到null。
  • dispatchTakePictureIntent方法中,uri变量未初始化,若intent.resolveActivity返回null,会直接返回未设置output的Intent,存在潜在风险。

解决方案

1. 复用预存的照片路径

在ImageCaptureManager中添加获取照片路径的方法,直接使用拍照前生成的路径,而非从返回的Intent中提取Uri:

// ImageCaptureManager类中添加
public String getCurrentPhotoPath() {
    return mCurrentPhotoPath;
}

2. 修复Uri初始化问题

确保dispatchTakePictureIntent中Uri始终被初始化,同时使用Android官方常量替代硬编码字符串:

public Intent dispatchTakePictureIntent() throws IOException {
    Uri uri = null; // 初始化Uri变量
    Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
    if (intent.resolveActivity(mContext.getPackageManager()) != null) {
        File imageFile = createImageFile();
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            uri = FileProvider.getUriForFile(mContext.getApplicationContext(),
                    mContext.getApplicationInfo().packageName + ".provider",
                    imageFile);
        } else {
            uri = Uri.fromFile(imageFile);
        }
        if (uri != null) {
            intent.putExtra(MediaStore.EXTRA_OUTPUT, uri);
        }
    }
    return intent;
}

3. 修正onActivityResult逻辑

直接使用预存的照片路径构建Uri,避免从返回的Intent中获取:

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if (requestCode == 1 && resultCode == RESULT_OK) {
        String photoPath = imageCaptureManager.getCurrentPhotoPath();
        if (photoPath != null) {
            File photoFile = new File(photoPath);
            Uri photoUri;
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
                photoUri = FileProvider.getUriForFile(this,
                        getPackageName() + ".provider",
                        photoFile);
            } else {
                photoUri = Uri.fromFile(photoFile);
            }
            // 处理图片输入流
            try (InputStream inputStream = getContentResolver().openInputStream(photoUri)) {
                // 你的图片处理逻辑
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

4. 验证FileProvider配置

确保AndroidManifest.xml中正确配置FileProvider:

<application>
    <provider
        android:name="androidx.core.content.FileProvider"
        android:authorities="${applicationId}.provider"
        android:exported="false"
        android:grantUriPermissions="true">
        <meta-data
            android:name="android.support.FILE_PROVIDER_PATHS"
            android:resource="@xml/file_paths" />
    </provider>
</application>

在res/xml目录下创建file_paths.xml,指定文件访问路径:

<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
    <external-files-path name="pictures" path="Pictures" />
</paths>

内容的提问来源于stack exchange,提问作者JustMeShortie

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.29 19:44:53