Android 调用系统剪裁工具剪裁用户头像
在Activity中加入以下代码段:
private final int CODE_CROP = 0x131;
//用于请求系统剪裁的请求码private Handler handler = new Handler() {
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
switch (msg.what){
case ImageCropUtil.Hand_Compress_Ok://图片压缩完成
modify_type = MODIFY_USER_HEAD_IMAGE;
File file = new File(ImageCropUtil.getHeadCompressPath());
//图片地址在ImageCropUtil中定义好的固定值
mFiles.put(file.getName(), file);
presenter.modifyUserHeadImage(mFiles);
break;
case ImageCropUtil.Hand_Compress_Failure://图片压缩失败
File file1 = new File(ImageCropUtil.ouputFilePath);
//用压缩之前的图片
mFiles.put(file1.getName(), file1);
presenter.modifyUserHeadImage(mFiles);
break;
}}
};
【Android 调用系统剪裁工具剪裁用户头像】
一、在用户选择好图片后掉用方法如下:(Activity中调用)
//跳转裁剪图片
ImageCropUtil.cropPhoto(this, headPath, CODE_CROP);
二、剪裁完成后调用压缩图片方法:【activity中的onActivityResult方法中调用】(可以不调用,如果不调用你就发送到服务端很可能报错:accep 427 byte but received 8192)
if (requestCode == CODE_CROP && resultCode == RESULT_OK) {
ImageCropUtil.compress15k(this, ImageCropUtil.ouputFilePath, handler);
}
三、剪裁完成后会返回到handler中
四、以下是ImageCropUtil类:
import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Matrix;
import android.media.ExifInterface;
import android.net.Uri;
import android.os.Environment;
import android.os.Handler;
import android.provider.MediaStore;
import android.util.DisplayMetrics;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
/**
* CreateTime 2017/9/18 16:10
* Author LiuShiHua
* Description:
*/public class ImageCropUtil {public static final int Hand_Compress_Ok = 0x66;
//图片压缩成功
public static final int Hand_Compress_Failure = 0x44;
//图片压缩失败//压缩后的图片文件地址
public static String getHeadCompressPath() {
return Environment.getExternalStorageDirectory() + "/ettda/temp/head_compress_output.jpg";
}//剪裁后的文件地址
public static final String ouputFilePath = Environment.getExternalStorageDirectory() + "/ettda/temp/head_output.jpg";
/**
* 裁剪原始的图片(系统自带的剪裁工具)
*
* @param activity 上下文
* @param filePath 图片源路径
* @param CODE_REQUEST_CROP 请求剪裁的请求码
*/
public static void cropPhoto(Activity activity, String filePath, int CODE_REQUEST_CROP) {
File file = new File(filePath);
if (!file.exists()) return;
File tempFile = new File(ouputFilePath);
if (!tempFile.exists()) {
File parent = tempFile.getParentFile();
parent.mkdirs();
try {
tempFile.createNewFile();
} catch (IOException e) {
e.printStackTrace();
}
}Uri uri = Uri.fromFile(tempFile);
Intent intent = new Intent("com.android.camera.action.CROP");
intent.setDataAndType(uri, "image/*");
intent.putExtra("crop", "true");
// 设置裁剪
intent.putExtra("aspectX", 1);
// aspectX , aspectY :宽高的比例
intent.putExtra("aspectY", 1);
intent.putExtra("outputX", 650);
// outputX , outputY : 裁剪图片宽高
intent.putExtra("outputY", 650);
//剪裁后过小时,拉伸
intent.putExtra("scale", true);
intent.putExtra("scaleUpIfNeeded", true);
/**
* 此方法返回的图片只能是小图片(sumsang测试为高宽160px的图片)
* 故将图片保存在Uri中,调用时将Uri转换为Bitmap,此方法还可解决miui系统不能return data的问题
*/
Uri uritempFile = Uri.parse("file://" + "/" + ouputFilePath);
//格式别搞错了
intent.putExtra(MediaStore.EXTRA_OUTPUT, uritempFile);
//输出图片文件
//是否返回bitmap对象
intent.putExtra("return-data", false);
intent.putExtra("outputFormat", Bitmap.CompressFormat.JPEG.toString());
activity.startActivityForResult(intent, CODE_REQUEST_CROP);
}/**
* 压缩图片文件(1.5M以下)
*
* @param context
* @param srcPath
* @return
*/
public static void compress15k(final Activity context, final String srcPath, final Handler handler) {
if (srcPath == null) {
handler.sendEmptyMessage(Hand_Compress_Failure);
return;
}
File file = new File(srcPath);
if (!file.exists()){
handler.sendEmptyMessage(Hand_Compress_Failure);
return;
}new Thread() {
@Override
public void run() {
super.run();
String pathNew = getHeadCompressPath();
File tempFile = new File(pathNew);
if (!tempFile.exists()) {
File parent = tempFile.getParentFile();
parent.mkdirs();
try {
tempFile.createNewFile();
} catch (IOException e) {
e.printStackTrace();
handler.sendEmptyMessage(Hand_Compress_Failure);
return;
}
}
String fileName = tempFile.getAbsolutePath();
DisplayMetrics dm = new DisplayMetrics();
context.getWindowManager().getDefaultDisplay().getMetrics(dm);
float hh = dm.heightPixels;
float ww = dm.widthPixels;
BitmapFactory.Options opts = new BitmapFactory.Options();
opts.inJustDecodeBounds = false;
int w = opts.outWidth;
int h = opts.outHeight;
int size = 0;
if (w <= ww && h <= hh) {
size = 1;
} else {
double scale = w >= h ? w / ww : h / hh;
double log = Math.log(scale) / Math.log(2);
double logCeil = Math.ceil(log);
size = (int) Math.pow(2, logCeil);
}
opts.inSampleSize = size;
Bitmap bitmap = BitmapFactory.decodeFile(srcPath, opts);
Matrix m = new Matrix();
m.postRotate(digreeBitmap(srcPath));
bitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), m, true);
ByteArrayOutputStream baos = new ByteArrayOutputStream();
int quality = 100;
bitmap.compress(Bitmap.CompressFormat.JPEG, quality, baos);
while (baos.toByteArray().length > 1536 * 1024) {//1.5M以下
baos.reset();
bitmap.compress(Bitmap.CompressFormat.JPEG, quality, baos);
quality -= 5;
}
try {
baos.writeTo(new FileOutputStream(fileName));
} catch (Exception e) {
e.printStackTrace();
handler.sendEmptyMessage(Hand_Compress_Failure);
return;
} finally {
try {
baos.flush();
baos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
handler.sendEmptyMessage(Hand_Compress_Ok);
}
}.start();
}private static int digreeBitmap(String imgpath) {
int digree = 0;
ExifInterface exif = null;
try {
exif = new ExifInterface(imgpath);
} catch (IOException e) {
e.printStackTrace();
exif = null;
}
if (exif != null) {
// 读取图片中相机方向信息
int ori = exif.getAttributeInt(ExifInterface.TAG_ORIENTATION, ExifInterface.ORIENTATION_UNDEFINED);
// 计算旋转角度
switch (ori) {
case ExifInterface.ORIENTATION_ROTATE_90:
digree = 90;
break;
case ExifInterface.ORIENTATION_ROTATE_180:
digree = 180;
break;
case ExifInterface.ORIENTATION_ROTATE_270:
digree = 270;
break;
default:
digree = 0;
break;
}
}
return digree;
}
}
推荐阅读
- android第三方框架(五)ButterKnife
- Android中的AES加密-下
- 带有Hilt的Android上的依赖注入
- SpringBoot调用公共模块的自定义注解失效的解决
- 如何在Mac中的文件选择框中打开系统隐藏文件夹
- thinkphp|thinkphp 3.2 如何调用第三方类库
- 单点登陆
- android|android studio中ndk的使用
- 操作系统|[译]从内部了解现代浏览器(1)
- 游乐园系统,助力游乐园管理