小组做数据库网站/微信群免费推广平台
最近在做类似注册的模块用到了上传头像
找了好几个demo效果都不太好,最后找了一个不会在Neux6 上crush掉的,代码也很简单:
项目叫ChangeHead
manifest文件内容:
-------------<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"package="com.example.changhead"android:versionCode="1"android:versionName="1.0" ><uses-sdk
android:minSdkVersion="8"android:targetSdkVersion="17" /><application
android:allowBackup="true"android:icon="@drawable/ic_launcher"android:label="@string/app_name"android:theme="@style/AppTheme" ><activity
android:name="com.example.changhead.MainActivity"android:label="@string/app_name" ><intent-filter><action android:name="android.intent.action.MAIN" /><category android:name="android.intent.category.LAUNCHER" /></intent-filter></activity></application><uses-permission android:name="android.permission.CAMERA"/><uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/><uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/>
</manifest>
MainActivity.java
package com.example.changhead;import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.provider.MediaStore;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ImageView;@SuppressLint("SdCardPath")
public class MainActivity extends Activity implements OnClickListener {private ImageView ivHead;//头像显示private Button btnTakephoto;//拍照private Button btnPhotos;//相册private Bitmap head;//头像Bitmapprivate static String path="/sdcard/myHead/";//sd路径@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);initView();}private void initView() {//初始化控件btnPhotos = (Button) findViewById(R.id.btn_photos);btnTakephoto = (Button) findViewById(R.id.btn_takephoto);btnPhotos.setOnClickListener(this);btnTakephoto.setOnClickListener(this);ivHead = (ImageView) findViewById(R.id.iv_head);Bitmap bt = BitmapFactory.decodeFile(path + "head.jpg");//从Sd中找头像,转换成Bitmapif(bt!=null){@SuppressWarnings("deprecation")Drawable drawable = new BitmapDrawable(bt);//转换成drawableivHead.setImageDrawable(drawable);}else{/*** 如果SD里面没有则需要从服务器取头像,取回来的头像再保存在SD中* */}}@Overridepublic void onClick(View v) {switch (v.getId()) {case R.id.btn_photos://从相册里面取照片 Intent intent1 = new Intent(Intent.ACTION_PICK, null);intent1.setDataAndType(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, "image/*");startActivityForResult(intent1, 1);break;case R.id.btn_takephoto://调用相机拍照Intent intent2 = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);intent2.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(new File(Environment.getExternalStorageDirectory(),"head.jpg")));startActivityForResult(intent2, 2);//采用ForResult打开break;default:break;}}protected void onActivityResult(int requestCode, int resultCode, Intent data) {switch (requestCode) {case 1: if (resultCode == RESULT_OK) {cropPhoto(data.getData());//裁剪图片}break;case 2:if (resultCode == RESULT_OK) {File temp = new File(Environment.getExternalStorageDirectory()+ "/head.jpg");cropPhoto(Uri.fromFile(temp));//裁剪图片}break;case 3:if (data != null) {Bundle extras = data.getExtras();head = extras.getParcelable("data");if(head!=null){/*** 上传服务器代码*/setPicToView(head);//保存在SD卡中ivHead.setImageBitmap(head);//用ImageView显示出来}}break;default:break;}super.onActivityResult(requestCode, resultCode, data);};/*** 调用系统的裁剪* @param uri*/public void cropPhoto(Uri uri) {Intent intent = new Intent("com.android.camera.action.CROP");intent.setDataAndType(uri, "image/*");intent.putExtra("crop", "true");// aspectX aspectY 是宽高的比例intent.putExtra("aspectX", 1);intent.putExtra("aspectY", 1);// outputX outputY 是裁剪图片宽高intent.putExtra("outputX", 150);intent.putExtra("outputY", 150);intent.putExtra("return-data", true);startActivityForResult(intent, 3);}private void setPicToView(Bitmap mBitmap) {String sdStatus = Environment.getExternalStorageState(); if (!sdStatus.equals(Environment.MEDIA_MOUNTED)) { // 检测sd是否可用 return; } FileOutputStream b = null;File file = new File(path);file.mkdirs();// 创建文件夹String fileName =path + "head.jpg";//图片名字try {b = new FileOutputStream(fileName);mBitmap.compress(Bitmap.CompressFormat.JPEG, 100, b);// 把数据写入文件} catch (FileNotFoundException e) {e.printStackTrace();} finally {try {//关闭流b.flush();b.close();} catch (IOException e) {e.printStackTrace();}}
}}
布局长这样…这个就不贴了,大家一看就明白.
然后我就改了一下存储的路径在自己项目下
+++++++++++++++++++++++++++++++++++++++
手机适配
测试的时候出了一个bug —当然是手机适配的问题;
在测试的手机中IUNI U3出现闪退
我迷茫了
找了很多网上的解决方案,然后我就请了一天的假,好好的在外面吃了一顿,第二天 我在github上找到一个 crop(截图)项目
CropMaster将上一个项目调用系统自带的截图部分替换成这个就OK了.
PS:注意为了能够重复的选择图片请加上项目给的Expample里的
++++++++++++++++++++++++++++++++++++++++++
++ resultView.setImageDrawable(null); ++
++++++++++++++++++++++++++++++++++++++++++Crop.pickImage(this);
这个项目是在另外一个项目上加工而成的cropimage如果要有白色框的效果请看theme里的配置.
恩,然后就解决了:-D
附:
由相机或图库中的图片bitmap与uri互相转换
1、bitmap to uri
Uri uri = Uri.parse(MediaStore.Images.Media.insertImage(getContentResolver(), bitmap, null,null));
2、uri to bitmap
Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), uri);
然而这并没有结束
跟很多人一样一样的,我又遇到了某些三星手机图片倒转的问题……
主要用到了三个方法
/*** Compress image by size, this will modify image width/height.* Used to get thumbnail** @param image* @param pixelW target pixel of width* @param pixelH target pixel of height* @return*/public Bitmap ratio(Bitmap image, float pixelW, float pixelH) {Bitmap bitmap = null;try {ByteArrayOutputStream os = new ByteArrayOutputStream();image.compress(Bitmap.CompressFormat.JPEG, 100, os);if (os.toByteArray().length / 1024 > 1024) {//判断如果图片大于1M,进行压缩避免在生成图片(BitmapFactory.decodeStream)时溢出os.reset();//重置baos即清空baosimage.compress(Bitmap.CompressFormat.JPEG, 50, os);//这里压缩50%,把压缩后的数据存放到baos中}ByteArrayInputStream is = new ByteArrayInputStream(os.toByteArray());BitmapFactory.Options newOpts = new BitmapFactory.Options();//开始读入图片,此时把options.inJustDecodeBounds 设回true了newOpts.inJustDecodeBounds = true;newOpts.inPreferredConfig = Bitmap.Config.RGB_565;bitmap = BitmapFactory.decodeStream(is, null, newOpts);newOpts.inJustDecodeBounds = false;int w = newOpts.outWidth;int h = newOpts.outHeight;float hh = pixelH;// 设置高度为240f时,可以明显看到图片缩小了float ww = pixelW;// 设置宽度为120f,可以明显看到图片缩小了//缩放比。由于是固定比例缩放,只用高或者宽其中一个数据进行计算即可int be = 1;//be=1表示不缩放if (w > h && w > ww) {//如果宽度大的话根据宽度固定大小缩放be = (int) (newOpts.outWidth / ww);} else if (w < h && h > hh) {//如果高度高的话根据宽度固定大小缩放be = (int) (newOpts.outHeight / hh);}if (be <= 0) be = 1;newOpts.inSampleSize = be;//设置缩放比例//重新读入图片,注意此时已经把options.inJustDecodeBounds 设回false了is = new ByteArrayInputStream(os.toByteArray());bitmap = BitmapFactory.decodeStream(is, null, newOpts);//压缩好比例大小后再进行质量压缩//return compress(bitmap, maxSize); // 这里再进行质量压缩的意义不大,反而耗资源,删除LogUtil.Debug("保存图片");FileOutputStream out = new FileOutputStream(temp);os.writeTo(out);LogUtil.Debug("已经保存");} catch (Exception e) {
// TODO: handle exceptione.printStackTrace();Log.e("--ImageFactory.ratio--", e.toString());}return bitmap;}/*** 读取图片的旋转的角度** @param path 图片绝对路径* @return 图片的旋转角度*/private int getBitmapDegree(String path) {int degree = 0;try {// 从指定路径下读取图片,并获取其EXIF信息ExifInterface exifInterface = new ExifInterface(path);// 获取图片的旋转信息int orientation = exifInterface.getAttributeInt(ExifInterface.TAG_ORIENTATION,ExifInterface.ORIENTATION_NORMAL);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;}/*** 将图片按照某个角度进行旋转** @param bm 需要旋转的图片* @param degree 旋转角度* @return 旋转后的图片*/public static Bitmap rotateBitmapByDegree(Bitmap bm, int degree) {Bitmap returnBm = null;// 根据旋转角度,生成旋转矩阵Matrix matrix = new Matrix();matrix.postRotate(degree);try {// 将原始图片按照旋转矩阵进行旋转,并得到新的图片returnBm = Bitmap.createBitmap(bm, 0, 0, bm.getWidth(), bm.getHeight(), matrix, true);} catch (OutOfMemoryError e) {}if (returnBm == null) {returnBm = bm;}if (bm != returnBm) {bm.recycle();}return returnBm;}