先贴出Google官方文档:Google官方拍照文档
感觉讲的不是很细,有不少坑。
先看需要配置权限和provider
<!--拍照存储权限-->
<uses-permission
android:name="android.permission.WRITE_EXTERNAL_STORAGE"
tools:ignore="ScopedStorage" />
<!--拍照权限-->
<uses-permission android:name="android.permission.CAMERA" />
<!--拍照需要配置provider为了兼容Android 7.0 下面的authorities里面的值需要和拍照里面的provider一样,下面这段代码
Uri photoUri = FileProvider.getUriForFile(activity, activity.getPackageName() + ".xiayiye5", photoFile);
-->
<provider
android:name="androidx.core.content.FileProvider"
android:authorities="${applicationId}.xiayiye5"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths">
</meta-data>
</provider>
再看下file_path文件如何写的
<?xml version="1.0" encoding="utf-8"?>
<paths>
<!-- 配置拍照图片存储路径为: 包名/files/Pictures-->
<external-path
name="my_images"
path="Android/data/cn.xiayiye5.xiayiye5library/files/Pictures" />
</paths>
当然还有一个万能路径写法待研究:感谢此博主:万能路径写法
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path
name="external"
path="." />
<external-files-path
name="external_files"
path="." />
<cache-path
name="cache"
path="." />
<external-cache-path
name="external_cache"
path="." />
<files-path
name="files"
path="." />
</paths>
————————————————
版权声明:本文为CSDN博主「Huc_Boy」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/liu_xueping/article/details/103980700
好了activity页面开始拍照了
public void dispatchTakePictureIntent(Activity activity) {
if (PackageManager.PERMISSION_GRANTED == ContextCompat.checkSelfPermission(activity, android.Manifest.permission.CAMERA)) {
//拍照方法
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
if (takePictureIntent.resolveActivity(activity.getPackageManager()) != null) {
File photoFile = null;
try {
photoFile = createImageFile(activity);
} catch (IOException ex) {
ex.printStackTrace();
}
if (photoFile != null) {
Uri photoUri = FileProvider.getUriForFile(activity, activity.getPackageName() + ".xiayiye5", photoFile);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, photoUri);
activity.startActivityForResult(takePictureIntent, TakePhotoActivity.REQUEST_IMAGE_CAPTURE);
}
}
} else {
//提示用户开户权限 拍照和读写sd卡权限
String[] perms = {Manifest.permission.READ_EXTERNAL_STORAGE, Manifest.permission.WRITE_EXTERNAL_STORAGE, Manifest.permission.CAMERA};
ActivityCompat.requestPermissions(activity, perms, 10010);
}
}
再看下activity页面回调
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REQUEST_IMAGE_CAPTURE && resultCode == RESULT_OK) {
//拍照后的图片回调
DisplayMetrics dm = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(dm);
int screenWidth = dm.widthPixels;
Bitmap decodeFile = BitmapFactory.decodeFile(TakePhotoUtils.getInstance().getImgPath());
int width = decodeFile.getWidth();
int size = width / screenWidth;
BitmapFactory.Options newOpts = new BitmapFactory.Options();
newOpts.inJustDecodeBounds = false;
//设置缩放比例
newOpts.inSampleSize = size * 2;
Log.e("打印缩放比例", size + "");
//重新读入图片,注意此时已经把options.inJustDecodeBounds 设回false了
Bitmap bitmap = BitmapFactory.decodeFile(TakePhotoUtils.getInstance().getImgPath(), newOpts);
ivTakePhoto.setImageBitmap(bitmap);
}
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
if (requestCode == 10010) {
boolean cameraAccepted = grantResults[0] == PackageManager.PERMISSION_GRANTED;
if (cameraAccepted) {
//权限申请成功
Toast.makeText(this, "activity页面权限申请成功!", Toast.LENGTH_LONG).show();
// 调用拍照方法
TakePhotoUtils.getInstance().dispatchTakePictureIntent(this);
} else {
//用户授权拒绝之后,友情提示一下就可以了
Toast.makeText(this, "activity页面请开启应用拍照权限!", Toast.LENGTH_LONG).show();
}
}
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
再看下在fragment中拍照只需要注意两点
看下在fragment中拍照的方法
public void dispatchTakePictureIntent(Fragment fragment) {
if (PackageManager.PERMISSION_GRANTED == ContextCompat.checkSelfPermission(fragment.getContext(), android.Manifest.permission.CAMERA)) {
//拍照方法
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
if (takePictureIntent.resolveActivity(fragment.requireActivity().getPackageManager()) != null) {
File photoFile = null;
try {
photoFile = createImageFile(fragment.requireActivity());
} catch (IOException ex) {
ex.printStackTrace();
}
if (photoFile != null) {
Uri photoUri = FileProvider.getUriForFile(fragment.requireActivity(), fragment.requireActivity().getPackageName() + ".xiayiye5", photoFile);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, photoUri);
//在fragment页面拍照需要使用fragment中的startActivityForResult,不然不会走fragment中的回调
fragment.startActivityForResult(takePictureIntent, TakePhotoActivity.REQUEST_IMAGE_CAPTURE);
}
}
} else {
//提示用户开户权限 拍照和读写sd卡权限
String[] perms = {Manifest.permission.READ_EXTERNAL_STORAGE, Manifest.permission.WRITE_EXTERNAL_STORAGE, Manifest.permission.CAMERA};
//在fragment中申请权限时候需要使用fragment中的requestPermissions方法不然不会走fragment中的回调
fragment.requestPermissions(perms, 10010);
}
}
再看下在fragment中的回调
@Override
public void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
// super.onActivityResult(requestCode, resultCode, data);
if (requestCode == TakePhotoActivity.REQUEST_IMAGE_CAPTURE && resultCode == RESULT_OK) {
//在fragment中拍照后的回调
DisplayMetrics dm = new DisplayMetrics();
requireActivity().getWindowManager().getDefaultDisplay().getMetrics(dm);
int screenWidth = dm.widthPixels;
Bitmap decodeFile = BitmapFactory.decodeFile(TakePhotoUtils.getInstance().getImgPath());
int width = decodeFile.getWidth();
int size = width / screenWidth;
BitmapFactory.Options newOpts = new BitmapFactory.Options();
newOpts.inJustDecodeBounds = false;
//设置缩放比例
newOpts.inSampleSize = size * 2;
Log.e("打印缩放比例", size + "");
//重新读入图片,注意此时已经把options.inJustDecodeBounds 设回false了
Bitmap bitmap = BitmapFactory.decodeFile(TakePhotoUtils.getInstance().getImgPath(), newOpts);
ivTakePhoto.setImageBitmap(bitmap);
}
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
//在fragment中申请权限后的回调
if (requestCode == 10010) {
boolean cameraAccepted = grantResults[0] == PackageManager.PERMISSION_GRANTED;
if (cameraAccepted) {
//权限申请成功
Toast.makeText(requireActivity(), "fragment页面权限申请成功!", Toast.LENGTH_LONG).show();
// 调用拍照方法
TakePhotoUtils.getInstance().dispatchTakePictureIntent(this);
} else {
//用户授权拒绝之后,友情提示一下就可以了
Toast.makeText(requireActivity(), "fragment页面请开启应用拍照权限!", Toast.LENGTH_LONG).show();
}
}
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
Activity拍照源码:activity拍照
Fragment拍照源码:fragment拍照
拍照工具类源码:拍照工具类