张晨的个人博客

Android调用系统相机照相和相册进行图片处理

张晨的个人博客2015-07-25安卓技术 2749 0A+A-

效果图:


首先需要在AndroidManifest.xml文件中添加权限:

<!--在SDCard中创建与删除文件权限-->
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS" />
<!-- 往SDCard写入数据权限 --> 
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> 
<!--请求访问使用照相设备-->
<uses-permission android:name="android.permission.CAMERA" /> 
<!--允许程序录制音频-->
<uses-permission android:name="android.permission.RECORD_AUDIO" /> 
<!--内外置sd卡写权限-->
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> 


activity_test.xml :

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical" 
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <Button
        android:id="@+id/camera"
        android:layout_marginTop="10dp"
        android:layout_width="match_parent"
        android:layout_height="50dp"
        android:text="照相"
        android:textColor="#FFFFFF"
        android:background="#FF9000"
        />

    <Button
        android:id="@+id/gallery"
        android:layout_marginTop="10dp"
        android:layout_width="match_parent"
        android:layout_height="50dp"
        android:text="相册"
        android:textColor="#FFFFFF"
        android:background="#FF9000"
        />

    <ImageView
        android:id="@+id/image"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:scaleType="fitXY"
        />

</LinearLayout>


TestsActivity.java:

package com.lykuaimai.kuaimaid.ui.activity;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.provider.MediaStore;
import android.support.v4.content.CursorLoader;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import com.lykuaimai.kuaimaid.R;
import com.lykuaimai.kuaimaid.utils.DateUtils;
import com.lykuaimai.kuaimaid.utils.FileUtils;
import java.io.File;
import java.util.Date;

/**
 * Created by Administrator on 2015/7/26.
 */
public class TestsActivity extends Activity implements View.OnClickListener{


    String savePath = "sdcard/kuaimaid/image/";
    String tempFileName;//临时文件路径
    String tempPhotoPath;//选择照片或者或拍照完成后保存的照片地址
    private static final int PHOTO_REQUEST_CAMERA = 1;// 拍照
    private static final int PHOTO_REQUEST_GALLERY = 2;// 从相册中选择

    Button camera;
    Button gallery;
    ImageView image;
    private Bitmap bitmap;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_test);
        camera = (Button) findViewById(R.id.camera);
        gallery = (Button) findViewById(R.id.gallery);
        image = (ImageView) findViewById(R.id.image);

        camera.setOnClickListener(this);
        gallery.setOnClickListener(this);
    }

    /**
     * 从相册获取
     */
    public void gallery() {
        // 激活系统图库,选择一张图片
        Intent intent = new Intent(Intent.ACTION_PICK);
        intent.setType("image/*");
        startActivityForResult(intent, PHOTO_REQUEST_GALLERY);
    }


    /*
     * 从拍照获取
     */
    public void camera() {
        Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        // 判断存储卡是否可以用,可用进行存储
        tempFileName = DateUtils.getDataString2(new Date())+".png";
        if (hasSdcard()) {
            //设定拍照存放到自己指定的目录,可以先建好
            File file = new File(savePath);
            if(!file.exists()){
                file.mkdirs();
            }
            intent.putExtra(MediaStore.EXTRA_OUTPUT,
                    Uri.fromFile(new File(savePath, tempFileName)));
        }
        startActivityForResult(intent, PHOTO_REQUEST_CAMERA);
    }

    /**
     返回结果处理
     */
    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent data) {

        try {
            if (requestCode == PHOTO_REQUEST_GALLERY) {//相册
                if (data != null) {
                    // 得到图片的全路径
                    Uri uri = data.getData();
                    tempPhotoPath = getRealPathFromURI(uri, this);
                    //根据自己的需求写压缩图片的大小
                    bitmap= compressImageFromFile(tempPhotoPath, 400f, 400f);
                    image.setImageBitmap(bitmap);//显示图片
                }

            } else if (requestCode == PHOTO_REQUEST_CAMERA) {//照相
			/*
				1.好些设备在调用系统相机照相后返回的 data为null
				  解决办法就是在调用相机之前先设定好照片的路径和名称,拍完后直接拿来用
				2.如果图片地址没有图片存在,则表示没有进行照相
			*/
                tempPhotoPath = savePath + "/" + tempFileName;
                File file = new File(tempPhotoPath);
                if(file.isFile()){//判断是否有照相
                    bitmap= compressImageFromFile(tempPhotoPath,400f,400f);
                    image.setImageBitmap(bitmap);//显示图片
                }


            }

        } catch (Exception e) {
            e.printStackTrace();
        }
        super.onActivityResult(requestCode, resultCode, data);
    }

    /**
     * 是否有sd卡
     * @return
     */
    public static boolean hasSdcard() {
        if (Environment.getExternalStorageState().equals(
                Environment.MEDIA_MOUNTED)) {
            return true;
        } else {
            return false;
        }
    }

    /**
     * 获取uri的文件地址
     * @param contentUri
     * @param context
     * @return
     */
    public String getRealPathFromURI(Uri contentUri,Context context) {
        String[] proj = { MediaStore.Images.Media.DATA };
        CursorLoader loader = new CursorLoader(context, contentUri, proj, null, null, null);
        Cursor cursor = loader.loadInBackground();
        int column_index = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
        cursor.moveToFirst();
        return cursor.getString(column_index);
    }

    /**
     * 压缩图片减少内存使用
     * @param srcPath
     * @param hh
     * @param ww
     * @return
     */
    public static Bitmap compressImageFromFile(String srcPath,float hh,float ww) {
        BitmapFactory.Options newOpts = new BitmapFactory.Options();
        newOpts.inJustDecodeBounds = true;// 只读边,不读内容
        Bitmap bitmap = BitmapFactory.decodeFile(srcPath, newOpts);

        newOpts.inJustDecodeBounds = false;
        int w = newOpts.outWidth;
        int h = newOpts.outHeight;
        /*float hh = 300f;// 长
        float ww = 300f;//   高*/
        int 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;// 设置采样率
        newOpts.inPreferredConfig = Bitmap.Config.ARGB_8888;// 该模式是默认的,可不设
        newOpts.inPurgeable = true;// 同时设置才会有效
        newOpts.inInputShareable = true;// 当系统内存不够时候图片自动被回收
        bitmap = BitmapFactory.decodeFile(srcPath, newOpts);
        return bitmap;
    }

    /** 回收Bitmap的空间。 */
    public void recyleBitmap(Bitmap bitmap) {
        if (bitmap != null && !bitmap.isRecycled()) {
            bitmap.recycle();
            bitmap = null;
        }
    }

    @Override
    public void onClick(View view) {
        switch (view.getId()){
            case R.id.camera :
                camera();//照相获取照片
                break;
            case R.id.gallery :
                gallery();//相册获取照片
                break;
        }
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        recyleBitmap(bitmap);//释放bitmap
    }


}


写的内容包含了图片压缩,URI转换,自己手写的测试可用~






文章关键词
android照相
android相册
发表评论