解决三星调用系统相机拍照显示图片旋转90度横着的问题

来源:互联网 发布:大乐透软件破解版 编辑:程序博客网 时间:2024/04/30 11:14

最近项目有个功能是调用系统相机拍照上传图片的功能,发现别的手机都没有ok,只有三星的显示图片很明显是旋转了90度,横着的。后来百度了解是三星对android相机单独做了优化(android碎片化,各种UI。。。你懂得)。所以要想根据路径显示图片时顺带读取图片的信息就行,ExifInterface(exif exchangeable image file) ,这个接口提供了图片文件的旋转,gps,时间等信息(具体的功能可以自行百度)。上代码:

// 从指定路径下读取图片,并获取其EXIF信息ExifInterface exifInterface = new ExifInterface(path);// 获取图片的旋转信息int orientation = exifInterface.getAttributeInt(ExifInterface.TAG_ORIENTATION,ExifInterface.ORIENTATION_NORMAL);Log.e("jxf", "orientation" + orientation);switch (orientation) {case ExifInterface.ORIENTATION_ROTATE_90:degree = 90;break;case ExifInterface.ORIENTATION_ROTATE_180:degree = 180;break;case ExifInterface.ORIENTATION_ROTATE_270:degree = 270;break;

所以我们根据图片的旋转角度信息在onActivityResult方法中将图片旋转过来就行了,这时我们就要用到Matrix这个类生产旋转矩阵:

// 得到图片的旋转角度int degree = getBitmapDegree(strImgPath);// 根据旋转角度,生成旋转矩阵Matrix matrix = new Matrix();matrix.postRotate(degree); Bitmap returnBm = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);

而我们想要的正确的图片就在这个returnBm对象中,我们只需imageView.setImageBitmap(returnBm);即可。

上面是我们实现适配三星的核心代码,下面将具体的相机util类奉上,由于我们项目中需要上传图片和图片名字, 所以会在调用相机拍照的同时返回图片名字,具体可以根据自己项目的具体需要自行调整:

/** * 调用系统相机拍照工具类 * @author yao * */public class CaremaUtil {private static String strImgPath = "";// 照片的绝对路径private static String imgPath = "";// 照片所在文件夹路径// 保存的拍照文件private static File out;/** * 相机照相并返回图片名字 */public static String cameraMethod(Activity activity, int requestCode) {// 实例化拍照的IntentIntent imageCaptureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);// 设置图片存放的路径,Environment.getExternalStorageDirectory()得到SD卡的根目录// 先验证手机是否有sdcardString status = Environment.getExternalStorageState();if ((Environment.MEDIA_MOUNTED).equals(status)) {strImgPath = getImgPath();// 本地保存原图File file = new File(strImgPath);Uri u = Uri.fromFile(file);imageCaptureIntent.putExtra(MediaStore.EXTRA_OUTPUT, u);// 启动ACITIVITYactivity.startActivityForResult(imageCaptureIntent, requestCode);LogUtil.log("imageName---" + getImageName());} else {Toast.makeText(activity, "没有储存卡", 0).show();}return getImageName();}/** * 返回图片的绝对路径 *  * @return */public static String getImgPath() {imgPath = getImagePath();// 存放照片的文件夹LogUtil.log("图片存放的路径-----" + strImgPath);String imageName = getImageName();LogUtil.log("图片全名路径---" + imageName);// 检查存放的路径是否存在,如果不存在则创建目录try {out = new File(imgPath);if (!out.exists()) {out.mkdirs();}// 在此目录下创建文件out = new File(imgPath, imageName);} catch (Exception e) {// TODO Auto-generated catch blocke.printStackTrace();}// 该照片的绝对路径strImgPath = imgPath + imageName;return strImgPath;}/** * 得到图片所在的文件夹的路径 *  * @return */public static String getImagePath() {return Environment.getExternalStorageDirectory().getAbsolutePath() + "//"+ SoftApplication.softApplication.getString(R.string.app_name) + "/approvalPic/";}/** * 得到图片的名字 *  * @return */public static String getImageName() {// 给相片命名String imageName = new SimpleDateFormat("yyyyMMddHHmmss").format(new Date()) + ".jpg";// 照片命名return imageName;}/** * 显示图片并得到图片字节字符串 *  * @param resultCode * @param data */public static String showPic(Activity activity, Intent data, ImageView imageView) {String iamgeStr = new String();File file = new File(strImgPath);try {Uri uri = Uri.fromFile(file);BitmapFactory.Options options = new BitmapFactory.Options();options.inJustDecodeBounds = true;// 简单的压缩BitmapFactory.decodeStream(activity.getContentResolver().openInputStream(uri), null, options);options.inSampleSize = 4;options.inJustDecodeBounds = false; // 压缩完后便可以将inJustDecodeBounds设置为false// 把流转化为Bitmap图片Bitmap bitmap = BitmapFactory.decodeStream(activity.getContentResolver().openInputStream(uri), null,options);android.provider.MediaStore.Images.Media.insertImage(activity.getContentResolver(), bitmap, null, null);activity.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, uri));// 得到图片的旋转角度int degree = getBitmapDegree(strImgPath);// 根据旋转角度,生成旋转矩阵Matrix matrix = new Matrix();matrix.postRotate(degree); Bitmap returnBm = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true); imageView.setImageBitmap(returnBm);ByteArrayOutputStream baos = new ByteArrayOutputStream();bitmap.compress(Bitmap.CompressFormat.PNG, 100, baos);byte[] bitmapByte = baos.toByteArray();iamgeStr = StringUtil.encodeStr(bitmapByte);LogUtil.log("iamgeStr", Log.ERROR, iamgeStr);// LogUtil.log("iamgeStr1", Log.ERROR, imageStr1);} catch (FileNotFoundException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();}return iamgeStr;}/** * 清除本地拍照缓存 */public static void clearCacheImage() {File filecache = new File(getImagePath());LogUtil.log("filecache---" + filecache.getPath());if (filecache != null && filecache.listFiles() != null) {for (File file : filecache.listFiles()) {if (file.isFile()) {file.delete(); // 删除所有文件LogUtil.log("删除所有文件");}}}}/** * 获取原始图片的角度(解决三星手机拍照后图片是横着的问题) * @param path 图片的绝对路径 * @return 原始图片的角度 */public static int getBitmapDegree(String path) {int degree = 0;try {// 从指定路径下读取图片,并获取其EXIF信息ExifInterface exifInterface = new ExifInterface(path);// 获取图片的旋转信息int orientation = exifInterface.getAttributeInt(ExifInterface.TAG_ORIENTATION,ExifInterface.ORIENTATION_NORMAL);Log.e("jxf", "orientation" + orientation);switch (orientation) {case ExifInterface.ORIENTATION_ROTATE_90:degree = 90;break;case ExifInterface.ORIENTATION_ROTATE_180:degree = 180;break;case ExifInterface.ORIENTATION_ROTATE_270:degree = 270;break;}} catch (IOException e) {e.printStackTrace();}return degree;}}

附上点击调用相机拍照的代码:
public void onClickEvent(View view) {switch (view.getId()) {case R.id.ll_customPic:// 客户合照imageName1 = CaremaUtil.cameraMethod(mContext, RESULT_CAPTURE_IMAGE_1);LogUtil.log("imageName1---" + imageName1);break;case R.id.ll_bar_scene:// 柜台场景imageName2 = CaremaUtil.cameraMethod(mContext, RESULT_CAPTURE_IMAGE_2);LogUtil.log("imageName2---" + imageName2);break;case R.id.btn_submit:// 提交submitWork();break;default:break;}}

这里面imageName1,imageName2是要上传的图片名字。

另外再附上onActivityResult中的代码:

@Overrideprotected void onActivityResult(int requestCode, int resultCode, Intent data) {super.onActivityResult(requestCode, resultCode, data);switch (requestCode) {case RESULT_CAPTURE_IMAGE_1:// 客户合照// 如果返回为正确的的结果if (resultCode == RESULT_OK) {imageStr1 = CaremaUtil.showPic(mContext, data, customPic);}break;case RESULT_CAPTURE_IMAGE_2:// 柜台照片// 如果返回为正确的的结果if (resultCode == RESULT_OK) {imageStr2 = CaremaUtil.showPic(mContext, data, barScene);}break;}}

这里面imageStr1,imageStr2是要上传图片的二进制流的字符串。


4 0
原创粉丝点击