最近在项目中用到了照相和相册取图剪裁上传头像,就在网上逛了逛,基本都是千篇一律,就弄下来用了用,没想到的是各种各样的奇葩问题就出现了。先给大家看看代码问题慢慢来解决
这是调用相机
1
2
3
4
5
6
7
8
9
10
|
public
static
File getImageFromCamer(Context context, File cameraFile,
int
REQUE_CODE_CAMERA, Intent intent) {
intent =
new
Intent(MediaStore.ACTION_IMAGE_CAPTURE);
File fileDir = HelpUtil.getFile(context,
"/Tour/user_photos"
);
cameraFile =
new
File(fileDir.getAbsoluteFile() +
"/"
+ System.currentTimeMillis() +
".jpg"
);
intent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(cameraFile));
((Activity) context).startActivityForResult(intent, REQUE_CODE_CAMERA);
return
cameraFile;
}
|
在这里我返回了一个file对象,这是应为项目中需要,大家可以不必真写,直接传一个Uri对象过来就好了
下面是调用相册
1
2
3
4
5
6
7
|
public
static
void
getImageFromPhoto(Context context,
int
REQUE_CODE_PHOTO) {
Intent intent =
new
Intent(Intent.ACTION_PICK,
null
);
intent.setDataAndType(MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
"image/*"
);
((Activity) context).startActivityForResult(intent, REQUE_CODE_PHOTO);
}
|
当然接下来是调用Activity的OnActivityResult了
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
|
@Override
protected
void
onActivityResult(
int
requestCode,
int
resultCode, Intent data) {
if
(resultCode == RESULT_OK) {
switch
(requestCode) {
case
ConstantUtil.REQUE_CODE_CAMERA:
uri = Uri.fromFile(cameraFile);
PhotoUtil.startPhotoZoom(context, uri,
ConstantUtil.REQUE_CODE_CROP);
break
;
case
ConstantUtil.REQUE_CODE_PHOTO:
if
(
null
!= data) {
//为了取消选取不报空指针用的
uri = data.getData();
PhotoUtil.startPhotoZoom(context, uri,
ConstantUtil.REQUE_CODE_CROP);
}
break
;
case
ConstantUtil.REQUE_CODE_CROP:
if
(uri==
null
){
break
;
}
cropBitmap=HelpUtil.getBitmapFromUri(uri,context);
if
(cropBitmap !=
null
) {
iv_headphoto.setImageBitmap(cropBitmap);
baos =
new
ByteArrayOutputStream();
cropBitmap.compress(Bitmap.CompressFormat.JPEG,
100
, baos);
headPicString =
new
String(Base64.encode(
baos.toByteArray(),
0
));
UploadPic(headPicString);
}
break
;
default
:
break
;
}
}
|
当然还有大家关心的剪切
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
|
public
static
void
startPhotoZoom(Context context, Uri uri,
int
REQUE_CODE_CROP) {
int
dp =
500
;
Intent intent =
new
Intent(
"com.android.camera.action.CROP"
);
intent.setDataAndType(uri,
"image/*"
);
// 下面这个crop=true是设置在开启的Intent中设置显示的VIEW可裁剪
intent.putExtra(
"crop"
,
"true"
);
intent.putExtra(
"scale"
,
true
);
// 去黑边
intent.putExtra(
"scaleUpIfNeeded"
,
true
);
// 去黑边
// aspectX aspectY 是宽高的比例
intent.putExtra(
"aspectX"
,
1
);
//输出是X方向的比例
intent.putExtra(
"aspectY"
,
1
);
// outputX outputY 是裁剪图片宽高,切忌不要再改动下列数字,会卡死
intent.putExtra(
"outputX"
, dp);
//输出X方向的像素
intent.putExtra(
"outputY"
, dp);
intent.putExtra(
"outputFormat"
, Bitmap.CompressFormat.JPEG.toString());
intent.putExtra(
"noFaceDetection"
,
true
);
intent.putExtra(MediaStore.EXTRA_OUTPUT, uri);
intent.putExtra(
"return-data"
,
false
);
//设置为不返回数据
((Activity) context).startActivityForResult(intent, REQUE_CODE_CROP);
}
|
在很多博客中都把“return-data”设置为了true然后在onActivityResult中通过data.getParcelableExtra("data")来获取数据,不过这样的话dp这个变量的值就不能太大了,不然你的程序就挂了。这里也就是我遇到问题的地方了,在大多数高配手机上这样用是没有问题的,不过很多低配手机就有点hold不住了,直接就异常了,包括我们的国产神机米3也没能hold住,所以我建议大家不要通过return data 大数据,小数据还是没有问题的,说以我们在剪切图片的时候就尽量使用Uri这个东东来帮助我们。
下面是我们进行剪裁用到的一些参数
Exta Options Table for image/* crop:
SetExtra | DataType | Description |
crop | String | Signals the crop feature |
aspectX | int | Aspect Ratio |
aspectY | int | Aspect Ratio |
outputX | int | width of output created from this Intent |
outputY | int | width of output created from this Intent |
scale | boolean | should it scale |
return-data | boolean | Return the bitmap with Action=inline-data by using the data |
data | Parcelable | Bitmap to process, you may provide it a bitmap (not tested) |
circleCrop | String | if this string is not null, it will provide some circular cr |
MediaStore.EXTRA_OUTPUT ("output") | URI | Set this URi to a File:///, see example code |
最后把通过Uri获得bitmap的方法给大家贴上
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
public
static
Bitmap getBitmapFromUri(Uri uri,Context mContext)
{
try
{
// 读取uri所在的图片
Bitmap bitmap = MediaStore.Images.Media.getBitmap(mContext.getContentResolver(), uri);
return
bitmap;
}
catch
(Exception e)
{
e.printStackTrace();
return
null
;
}
}
|