本文实例为大家分享了Android选择相机和系统相册的具体代码,供大家参考,具体内容如下
说明:
Android选择相机和系统相册
代码:
1、打开系统相机和系统相册工具类
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
|
package com.gxjl.pe.gxjlpesdk.util; import android.Manifest; import android.app.Activity; import android.app.ActivityManager; import android.app.AlertDialog; import android.content.Context; import android.content.DialogInterface; import android.content.Intent; import android.content.pm.PackageManager; import android.graphics.Bitmap; import android.net.Uri; import android.os.Build; import android.provider.MediaStore; import android.support.v4.app.ActivityCompat; import android.support.v4.content.ContextCompat; import android.support.v4.content.FileProvider; import android.widget.Toast; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.IOException; import java.util.ArrayList; import java.util.List; /** * 图片工具类 * Created by xiaoshuai on 2018/8/17. */ public class ImgUtil { public static final int TAKE_PHOTO = 1 ; //拍照 public static final int CHOOSE_PHOTO = 2 ; //选择相册 public static final int REQUEST_CODE_CAMERA = 3 ; //相机权限请求 public static final int REQUEST_CODE_ALBUM = 4 ; //相册权限请求 public static Uri imageUri; //相机拍照图片保存地址 /** * 选择图片,从图库、相机 * * @param activity 上下文 */ public static void choicePhoto( final Activity activity) { //采用的是系统Dialog作为选择弹框 new AlertDialog.Builder(activity).setTitle( "上传头像" ) //设置对话框标题 .setPositiveButton( "拍照" , new DialogInterface.OnClickListener() { //添加确定按钮 @Override public void onClick(DialogInterface dialog, int which) { if (Build.VERSION.SDK_INT >= 23 ) { //检查相机权限 ArrayList<String> permissions = new ArrayList<>(); if (activity.checkSelfPermission(Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) { permissions.add(Manifest.permission.CAMERA); } if (permissions.size() == 0 ) { //有权限,跳转 //打开相机-兼容7.0 openCamera(activity); } else { activity.requestPermissions(permissions.toArray( new String[permissions.size()]), REQUEST_CODE_CAMERA); } } else { //打开相机-兼容7.0 openCamera(activity); } } }). setNegativeButton( "系统相册" , new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { //如果有权限申请,请在Activity中onRequestPermissionsResult权限返回里面重新调用openAlbum() if (ContextCompat.checkSelfPermission(activity, Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) { ActivityCompat.requestPermissions(activity, new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, REQUEST_CODE_ALBUM); } else { openAlbum(activity); } } }).show(); //在按键响应事件中显示此对话框 } /** * 打开相机 * 兼容7.0 * * @param activity */ public static void openCamera(Activity activity) { // 创建File对象,用于存储拍照后的图片 File outputImage = new File(activity.getExternalCacheDir(), "output_image.jpg" ); try { if (outputImage.exists()) { outputImage.delete(); } outputImage.createNewFile(); } catch (IOException e) { e.printStackTrace(); } if (Build.VERSION.SDK_INT < 24 ) { imageUri = Uri.fromFile(outputImage); } else { //Android 7.0系统开始 使用本地真实的Uri路径不安全,使用FileProvider封装共享Uri //参数二:fileprovider绝对路径 com.dyb.testcamerademo:项目包名 imageUri = FileProvider.getUriForFile(activity, "com.mandaotech.ewallet.fileprovider" , outputImage); } // 启动相机程序 Intent intent = new Intent( "android.media.action.IMAGE_CAPTURE" ); intent.putExtra(MediaStore.EXTRA_OUTPUT, imageUri); activity.startActivityForResult(intent, TAKE_PHOTO); } /** * 打开图库 * @param activity */ public static void openAlbum(Activity activity) { //调用系统图库的意图 Intent choosePicIntent = new Intent(Intent.ACTION_PICK, null ); choosePicIntent.setDataAndType(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, "image/*" ); activity.startActivityForResult(choosePicIntent, CHOOSE_PHOTO); //打开系统默认的软件 //Intent intent = new Intent("android.intent.action.GET_CONTENT"); //intent.setType("image/*"); //activity.startActivityForResult(intent, CHOOSE_PHOTO); // 打开相册 } /** * 得到byte[] * 这里对传入的图片Uri压缩到1M以内,并转换为byte[]后返回 * * @param activity 上下文 * @param uri 传入图片的Uri * @return byte[] */ public static byte [] getImgByteFromUri(Activity activity, Uri uri) throws IOException { Bitmap bitmap = MediaStore.Images.Media.getBitmap(activity.getContentResolver(), uri); ByteArrayOutputStream out = new ByteArrayOutputStream(); bitmap.compress(Bitmap.CompressFormat.PNG, 100 , out); //100表示不压缩,直接放到out里面 int options = 90 ; //压缩比例 while (out.toByteArray().length / 1024 > 200 ) { // 循环判断如果压缩后图片是否大于100kb,大于继续压缩 out.reset(); // 重置baos即清空baos bitmap.compress(Bitmap.CompressFormat.JPEG, options, out); // 这里压缩options%,把压缩后的数据存放到baos中 options -= 10 ; // 每次都减少10 } byte [] bs = out.toByteArray(); return bs; } } |
相机选择:采用固定地址选择大图方式,上段代码块是适配7.0的,因为Android 7.0系统开始 使用本地真实的Uri路径不安全,使用FileProvider封装共享Uri。其中android:name、exported、 android:grantUriPermissions、取值固定,android:authorities取值为:“自己项目包名”.fileprovider。
2、申请权限确认
工具类中点击申请权限,可以在Activity中检测用户是否同意了权限
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
@Override public void onRequestPermissionsResult( int requestCode, String[] permissions, int [] grantResults) { switch (requestCode) { case REQUEST_CODE_ALBUM: //相册存储权限 if (grantResults.length > 0 && grantResults[ 0 ] == PackageManager.PERMISSION_GRANTED) { ImgUtil.openAlbum( this ); } else { UiUtil.showToast( this , "选择图库需要同意权限" ); } break ; case REQUEST_CODE_CAMERA: //相机拍照权限 if (grantResults[ 0 ] == PackageManager.PERMISSION_GRANTED) { //允许 ImgUtil.openCamera(OcrHandReviewActivity. this ); } else { //拒绝 UiUtil.showToast( this , "只有同意相机权限,才能使用扫码功能" ); } break ; default : } } |
3、相机和相册放回
在activity中得到拍照和选择的图片
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
|
//相机、相册、剪切 返回 @Override public void onActivityResult( int requestCode, int resultCode, Intent data) { //正确返回 if (resultCode == RESULT_OK) { switch (requestCode) { case ImgUtil.TAKE_PHOTO: //相机返回 Log.e( "返回相机" , ImgUtil.imageUri.toString()); GlideApp.with(ElecIdPAActivity. this ) .load(ImgUtil.imageUri) .skipMemoryCache( true ) .diskCacheStrategy( DiskCacheStrategy.NONE ) .into(iv_zhengmain_photo); break ; case ImgUtil.CHOOSE_PHOTO: //相册返回 try { if (data != null ) { //相册返回 Uri uri = data.getData(); Log.e( "返回相册" , uri.toString()); GlideApp.with(ElecIdPAActivity. this ) .load(uri) .skipMemoryCache( true ) .diskCacheStrategy( DiskCacheStrategy.NONE ) .into(iv_zhengmain_photo); } } catch (Exception e) { e.printStackTrace(); UiUtil.showToast( this , "图片选择失败" ); } break ; } } else { UiUtil.showToast( this , "图片选择失败" ); } } |
4、AndroidManifest.xml权限声明
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
|
<!--获取sd卡写的权限,用于文件上传和下载--> < uses-permission android:name = "android.permission.WRITE_EXTERNAL_STORAGE" /> < uses-permission android:name = "android.permission.READ_EXTERNAL_STORAGE" /> <!--允许读取手机状态--> < uses-permission android:name = "android.permission.READ_PHONE_STATE" /> <!-- 相机权限 --> < uses-permission android:name = "android.permission.CAMERA" /> < uses-permission android:name = "android.permission.VIBRATE" /> < uses-permission android:name = "android.permission.FLASHLIGHT" /> < application <!--7.0相机权限--> < provider android:name = "android.support.v4.content.FileProvider" android:authorities = "com.dyb.testcamerademo.fileprovider" android:exported = "false" android:grantUriPermissions = "true" > < meta-data android:name = "android.support.FILE_PROVIDER_PATHS" android:resource = "@xml/file_paths" /> </ provider > |
5、file_paths.xml
android:resource=“@xml/file_paths”中@xml/的文件名字可以随便起,但一般规范化都用此名。
xml包下(在res下面新建包xml,然后在xml下面新建file_paths.xml文件)
* file_paths.xml源码
1
2
3
4
5
6
7
8
9
10
11
12
13
|
<? xml version = "1.0" encoding = "utf-8" ?> < paths xmlns:android = "http://schemas.android.com/apk/res/android" > <!-- name属性的值可以随便写,别名 path属性的值表示共享的具体位置,设置空就表示将整个SD卡进行共享 --> < paths > < external-path name = "camera_photos" path = "" /> </ paths > </ paths > |
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持服务器之家。
原文链接:https://blog.csdn.net/u012246458/article/details/79640980