zoukankan      html  css  js  c++  java
  • Android中实现自定义的拍照应用

    可以参考:http://www.android-doc.com/guide/topics/media/camera.html

    一、添加相应的权限

     <uses-permission android:name="android.permission.CAMERA" />
        <uses-feature android:name="android.hardware.camera" /><!-- 拍照的功能 -->
        <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
    
    
    
    
    
     <activity
                android:name=".MainActivity"
                android:label="@string/app_name" 
                android:screenOrientation="landscape"><!-- 写死横屏 -->
                <intent-filter>
                    <action android:name="android.intent.action.MAIN" />
    
                    <category android:name="android.intent.category.LAUNCHER" />
                </intent-filter>
     </activity>

    二、布局文件的配置

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:orientation="horizontal"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        >
      <FrameLayout
        android:id="@+id/camera_preview"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:layout_weight="1"
        />
    
      <Button
        android:id="@+id/button_capture"
        android:text="Capture"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        />
    </LinearLayout>

    三、系统关键代码和注释

    创建预览类CameraPreview:

    import java.io.IOException;
    
    import android.content.Context;
    import android.hardware.Camera;
    import android.util.Log;
    import android.view.SurfaceHolder;
    import android.view.SurfaceView;
    
    /** A basic Camera preview class */
    public class CameraPreview extends SurfaceView implements SurfaceHolder.Callback {
        public static final String TAG = "camera";
        private SurfaceHolder mHolder;
        private Camera mCamera;
    
        public CameraPreview(Context context, Camera camera) {
            super(context);
            mCamera = camera;
    
            // Install a SurfaceHolder.Callback so we get notified when the
            // underlying surface is created and destroyed.
            //获取surfaceview的控制器
            mHolder = getHolder();
            //创建侦听
            mHolder.addCallback(this);
            // deprecated setting, but required on Android versions prior to 3.0
            mHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
        }
    
        public void surfaceCreated(SurfaceHolder holder) {
            // The Surface has been created, now tell the camera where to draw the preview.
            try {
                //设置摄像头预览界面在holder对应的那个surfaceview
                mCamera.setPreviewDisplay(holder);
                //开始预览
                mCamera.startPreview();
            } catch (IOException e) {
                Log.d(TAG, "Error setting camera preview: " + e.getMessage());
            }
        }
    
        public void surfaceDestroyed(SurfaceHolder holder) {
            // empty. Take care of releasing the Camera preview in your activity.
        }
    
        public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {
            // If your preview can change or rotate, take care of those events here.
            // Make sure to stop the preview before resizing or reformatting it.
    
            if (mHolder.getSurface() == null){
              // preview surface does not exist
              return;
            }
    
            // stop preview before making changes
            try {
                mCamera.stopPreview();
            } catch (Exception e){
              // ignore: tried to stop a non-existent preview
            }
    
            // set preview size and make any resize, rotate or
            // reformatting changes here
    
            // start preview with new settings
            try {
                mCamera.setPreviewDisplay(mHolder);
                mCamera.startPreview();
    
            } catch (Exception e){
                Log.d(TAG, "Error starting camera preview: " + e.getMessage());
            }
        }
    }

    主类MainActivity:

    import java.io.File;
    import java.io.FileNotFoundException;
    import java.io.FileOutputStream;
    import java.io.IOException;
    
    import android.app.Activity;
    import android.content.Context;
    import android.content.pm.PackageManager;
    import android.hardware.Camera;
    import android.hardware.Camera.AutoFocusCallback;
    import android.hardware.Camera.PictureCallback;
    import android.os.Bundle;
    import android.util.Log;
    import android.view.View;
    import android.widget.Button;
    import android.widget.FrameLayout;
    
    public class MainActivity extends Activity {
    
        private Camera mCamera;
        private CameraPreview mPreview;
    
        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
    
            if(checkCameraHardware(this)){
                // Create an instance of Camera
                //创建摄像头实例
                mCamera = getCameraInstance();
            } else {
                return;
            }
    
            // Create our Preview view and set it as the content of our activity.
            //创建预览类的对象
            mPreview = new CameraPreview(this, mCamera);
            FrameLayout preview = (FrameLayout) findViewById(R.id.camera_preview);
            //把预览类设置为帧布局的子节点
            preview.addView(mPreview);
            
            
            //给按钮设置监听
            Button captureButton = (Button) findViewById(R.id.button_capture);
            captureButton.setOnClickListener(
                new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        //设置聚焦
                        mCamera.autoFocus(new AutoFocusCallback() {
                            
                            @Override
                            public void onAutoFocus(boolean success, Camera camera) {
                                 //进行拍照
                                mCamera.takePicture(null, null, mPicture);
                            }
                        });
                       
                    }
                }
            );
        }
    
        
        /** 检测手机是否有摄像头 */
        private boolean checkCameraHardware(Context context) {
            if (context.getPackageManager().hasSystemFeature(PackageManager.FEATURE_CAMERA)){
                // this device has a camera
                return true;
            } else {
                // no camera on this device
                return false;
            }
        }
        
        /** 一个获取摄像头对象的安全实例 */
        public static Camera getCameraInstance(){
            Camera c = null;
            try {
                c = Camera.open(); //获取第一个后置摄像头的实例
            }
            catch (Exception e){
                // Camera is not available (in use or does not exist)
            }
            return c; // returns null if camera is unavailable
        }
        
        private PictureCallback mPicture = new PictureCallback() {
    
            //拍照时会调用此方法
            //data:照片的字节数组
            @Override
            public void onPictureTaken(byte[] data, Camera camera) {
    
                try {
                    File pictureFile = new File("sdcard/mr.jpg");
                    FileOutputStream fos = new FileOutputStream(pictureFile);
                    fos.write(data);
                    fos.close();
                } catch (FileNotFoundException e) {
                    Log.d(CameraPreview.TAG, "File not found: " + e.getMessage());
                } catch (IOException e) {
                    Log.d(CameraPreview.TAG, "Error accessing file: " + e.getMessage());
                } finally {
                    //拍照完成后重新进入预览
                    camera.startPreview();
                }
            }
        };
    
    }

    显示效果:

  • 相关阅读:
    POJ 1659 Frogs' Neighborhood
    zoj 2913 Bus Pass(BFS)
    ZOJ 1008 Gnome Tetravex(DFS)
    POJ 1562 Oil Deposits (DFS)
    zoj 2165 Red and Black (DFs)poj 1979
    hdu 3954 Level up
    sgu 249 Matrix
    hdu 4417 Super Mario
    SPOJ (BNUOJ) LCM Sum
    hdu 2665 Kth number 划分树
  • 原文地址:https://www.cnblogs.com/DarrenChan/p/5639596.html
Copyright © 2011-2022 走看看