android调用相机获取图片程序全代码,附Unable to get provider android.support.v4.content.FileProvider和其他一些坑最简单有效的解决办法

经过一个小时的不断试错,发现网上说的什么mutiDex那些简直是瞎扯。

真正的解决办法是在AndroidManifest.xml中的provider的android:name设置为"androidx.core.content.FileProvider",不要再傻傻的去加什么compile鬼东西了。

 

下面附上一个调用相机获取图片的完整可用程序。

界面布局:一个ImageView和一个Button。只有一个Activity叫MainActivity。

在res文件夹下创建一个xml文件夹,里面创建一个名字叫file_paths.xml的文件

file_paths.xml

注意:

如果图片位置是在getFilesDir()下任意位置的话(我这个程序就是),节点类型就是files-path

如果图片位置是在getFilesDir()下任意位置的话,节点类型就是external-path

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

AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.cyy.camera">

    <uses-permission android:name="android.permission.CAMERA"/>
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    <uses-permission android:name="android.permission.INTERNET"/>
    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">
        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
        <provider
            android:name="androidx.core.content.FileProvider"
            android:authorities="com.cyy.camera.provider"
            android:exported="false"
            android:grantUriPermissions="true">
            <meta-data
                android:name="android.support.FILE_PROVIDER_PATHS"
                android:resource="@xml/file_paths">
            </meta-data>
        </provider>
    </application>

</manifest>

MainActivity.java

package com.cyy.camera;

import android.Manifest;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.net.Uri;
import android.os.Bundle;
import android.provider.MediaStore;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.Toast;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.app.ActivityCompat;
import androidx.core.content.ContextCompat;
import androidx.core.content.FileProvider;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;

import static androidx.core.content.PermissionChecker.PERMISSION_GRANTED;

public class MainActivity extends AppCompatActivity {

    private ImageView imageView;
    private static int GET_PHOTO=0;
    private Uri fileUri;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Button button = findViewById(R.id.button);
        button.setOnClickListener(new TakePhoto());
        imageView=findViewById(R.id.imageView);
        RequestPermission();
    }

    private void RequestPermission(){
        String[] permissions=new String[]{
                Manifest.permission.CAMERA,
                Manifest.permission.WRITE_EXTERNAL_STORAGE,
                Manifest.permission.INTERNET,
                Manifest.permission.READ_EXTERNAL_STORAGE
        };
        for (String permission : permissions) {
            if ((ContextCompat.checkSelfPermission(this, permission) != PERMISSION_GRANTED)) {
                ActivityCompat.requestPermissions(this, permissions, 0);
            }
        }
    }

    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        for (int i=0;i<permissions.length;i++){
            String permission=permissions[i];
            if(!ActivityCompat.shouldShowRequestPermissionRationale(MainActivity.this,permission)){
                AlertDialog.Builder builder=new AlertDialog.Builder(MainActivity.this);
                builder.setTitle("提醒");
                builder.setMessage("请去往设置页为本程序授予权限,否则将无法使用");
                builder.setPositiveButton("确定", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        System.exit(0);
                    }
                });
                AlertDialog alertDialog=builder.create();
                alertDialog.setCanceledOnTouchOutside(false);
                return;
            }
            else if(grantResults[i]!=PERMISSION_GRANTED){
                AlertDialog.Builder builder=new AlertDialog.Builder(MainActivity.this);
                builder.setTitle("提醒");
                builder.setMessage("请授予权限,否则将无法使用程序");
                builder.setPositiveButton("确定",null);
                builder.create().show();
                return;
            }
        }
    }

    private class TakePhoto implements View.OnClickListener{

        @Override
        public void onClick(View v) {
            File imageFile=new File(getFilesDir(),"CameraApp/abc.jpg");
            try {
                File dir=new File(getFilesDir(),"CameraApp");
                if(!dir.exists()){
                    if(!dir.mkdirs()){
                        Toast.makeText(MainActivity.this, "无法创建缓存文件", Toast.LENGTH_LONG).show();
                        return;
                    }
                }
                Toast.makeText(MainActivity.this,dir.toString(),Toast.LENGTH_LONG).show();
                while(!imageFile.createNewFile()){
                    if(!imageFile.delete()){
                        Toast.makeText(MainActivity.this, "无法创建缓存文件", Toast.LENGTH_LONG).show();
                        return;
                    }
                }
                Intent intent=new Intent("android.media.action.IMAGE_CAPTURE");
                fileUri= FileProvider.getUriForFile(MainActivity.this,"com.cyy.camera.provider",imageFile);
                intent.putExtra(MediaStore.EXTRA_OUTPUT,fileUri);
                startActivityForResult(intent,GET_PHOTO);
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
        if (requestCode == GET_PHOTO) {
            try {
                Bitmap bitmap= BitmapFactory.decodeStream(getContentResolver().openInputStream(fileUri));
                imageView.setImageBitmap(bitmap);
            } catch (FileNotFoundException e) {
                e.printStackTrace();
            }
        }
        super.onActivityResult(requestCode, resultCode, data);
    }
}

谷歌越更新越复杂,适配的版本越多,真希望统一一下标准,以后就别改了。

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值