您的位置:首页 > 移动开发 > Android开发

android 自定义Camera控件

2016-01-16 16:09 585 查看
简单实现Camera自定义控件:

效果图:



具体代码解释在代码中有记录,主要代码如下:

先看下布局文件:

activity_camera.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:gravity="center"
tools:context=".MainActivity">

<com.example.vic.myapplication.CustomCamera
android:id="@+id/camera"
android:layout_width="match_parent"
android:layout_height="match_parent"/>

<ImageView
android:layout_marginBottom="8dp"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@mipmap/iv_takephoto"
android:onClick="takePhoto"
/>
</RelativeLayout>


CameraActivity.java

package com.example.vic.myapplication;

import android.os.Bundle;
import android.view.MotionEvent;
import android.view.View;

import com.example.vic.myapplication.base.BaseActivity;

/**
* Created by Administrator on 2016/1/14.
*/
public class CameraActivity extends BaseActivity {
private CustomCamera customCamera;

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setToolBarInfo(true);
getToolBar_center().setText("Camera");
setContentLayout(R.layout.activity_camera);

customCamera = (CustomCamera) findViewById(R.id.camera);

}

@Override
public boolean onTouchEvent(MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_DOWN) {
customCamera.autoFocus(false);
return true;
}
return super.onTouchEvent(event);
}

public void takePhoto(View v) {
customCamera.autoFocus(true);
}

}


下面的CustomCamera.java

package com.example.vic.myapplication;

import android.app.Activity;
import android.content.Context;
import android.content.pm.PackageManager;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.ImageFormat;
import android.graphics.Matrix;
import android.hardware.Camera;
import android.os.Environment;
import android.text.format.Time;
import android.util.AttributeSet;
import android.view.Surface;
import android.view.SurfaceHolder;
import android.view.SurfaceView;

import com.example.vic.myapplication.utils.AppLog;
import com.example.vic.myapplication.utils.AppToast;

import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/**
* Created by Administrator on 2016/1/14.
*/
public class CustomCamera extends SurfaceView implements SurfaceHolder.Callback {

private Camera camera;
private SurfaceHolder holder;
private Context context;
private String picUrl;

public CustomCamera(Context context, AttributeSet attrs) {
super(context, attrs);
this.context = context;
initHolder();
}

private void initHolder() {
//实例holder
holder = this.getHolder();
//设置屏常 亮
holder.setKeepScreenOn(true);
//增加一个回调
holder.addCallback(this);
}

/**
* 判断是否存在摄像头
* @param context
* @return
*/
private boolean existCamera(Context context) {
return context.getPackageManager().hasSystemFeature(PackageManager.FEATURE_CAMERA);
}

/**
* 初始化相机
* 0    表示后置camera
* Camera.getNumberOfCameras()-1  可调用前置camera
*/
private void initCamera() {
if (camera == null) {
//            camera = Camera.open(Camera.getNumberOfCameras() - 1);//前置摄像头
camera = Camera.open();
}
}

private void imagePreview(SurfaceHolder holder) {
try {
if (camera != null) {
//设置预览显示到holder
camera.setPreviewDisplay(holder);
//系统默认是横向的, 所以要设置方向为顺时针90度
camera.setDisplayOrientation(90);
//开始预览
camera.startPreview();
}
} catch (IOException e) {
e.printStackTrace();
}

}

private void setParameters() {
if (camera != null) {
//获取相机的参数设置对象
Camera.Parameters parameters = camera.getParameters();
//设置图片格式
parameters.setPictureFormat(ImageFormat.JPEG);
//设置自动闪光灯
parameters.setFlashMode(Camera.Parameters.FLASH_MODE_AUTO);
//对parametrs对象进行修改后,重新赋值
camera.setParameters(parameters);
}
}

private void releaseCamera() {
if (camera != null) {
//取消预览回调
camera.setPreviewCallback(null);
//停止预览
camera.stopPreview();
//释放camera
camera.release();
//置空
camera = null;
}
}

/**
* 自动聚焦
* @param b  ture为自动聚焦后,就拍照, false为只自动聚焦
*/
public void autoFocus(final boolean b) {
if (camera != null) {
camera.autoFocus(new Camera.AutoFocusCallback() {
@Override
public void onAutoFocus(boolean success, Camera camera) {
if (success) {
if (b)
takePicture();
}

}
});
}
}

public void takePicture() {
if (camera != null) {
camera.takePicture(null, null, new Camera.PictureCallback() {
@Override
public void onPictureTaken(byte[] data, Camera camera) {

// data就是图片信息
//声明bitmap对象
Bitmap bMap;
try {
//将数据读到bitmap
bMap = BitmapFactory.decodeByteArray(data, 0, data.length);
//系统默认返回图片是横向的,下面操作对照片就行旋转90度
Bitmap bMap2;
Matrix matrix = new Matrix();
matrix.reset();
matrix.setRotate(90);
bMap2 = Bitmap.createBitmap(bMap, 0, 0, bMap.getWidth(),
bMap.getHeight(), matrix, true);
bMap = bMap2;
//照片保存

if (picUrl == null) {
picUrl = Environment.getExternalStorageDirectory() + File.separator +pictureName()+".jpg";
}
File file = new File(picUrl);
if (file.exists()) {
file.delete();
}
BufferedOutputStream bos =
new BufferedOutputStream(new FileOutputStream(file));
bMap.compress(Bitmap.CompressFormat.JPEG, 100, bos);//将图片压缩到流中
bos.flush();//输出
bos.close();//关闭

bMap.recycle();
bMap2.recycle();
//保存后,重新预览
imagePreview(holder);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
}

@Overrid
4000
e
public void surfaceCreated(SurfaceHolder holder) {
if (existCamera(context)) {
initCamera();
}
}

@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
AppLog.Log("surfaceChanged()");
setParameters();
imagePreview(holder);
}

@Override
public void surfaceDestroyed(SurfaceHolder holder) {
AppLog.Log("surfaceDestroyed()");
releaseCamera();
}

public void setPicUrl(String picUrl) {
this.picUrl = picUrl;
AppLog.Log("setPicUrl()");
}

public String pictureName() {
String str = "";
Time t = new Time();
t.setToNow(); // 取得系统时间。
int year = t.year;
int month = t.month + 1;
int date = t.monthDay;
int hour = t.hour; // 0-23
int minute = t.minute;
int second = t.second;
if (month < 10)
str = String.valueOf(year) + "0" + String.valueOf(month);
else {
str = String.valueOf(year) + String.valueOf(month);
}
if (date < 10)
str = str + "0" + String.valueOf(date + "_");
else {
str = str + String.valueOf(date + "_");
}
if (hour < 10)
str = str + "0" + String.valueOf(hour);
else {
str = str + String.valueOf(hour);
}
if (minute < 10)
str = str + "0" + String.valueOf(minute);
else {
str = str + String.valueOf(minute);
}
if (second < 10)
str = str + "0" + String.valueOf(second);
else {
str = str + String.valueOf(second);
}
return str;
}
}


最后不要忘了,添加权限:

<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

<uses-feature android:name="android.hardware.camera" />
<uses-feature android:name="android.hardware.camera.autofocus" />
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息