`

Android 调用系统Camera 程序照相,获取照片

阅读更多

下面是我自己整理的源码,网络上好多不能够运行,或者有bug。
我在emulator android 2.1运行良好,源码注释一定程度能够自我解释
强烈推荐配合adb locat Take2:d *:s查看程序运行函数调用情况

对Activity生命周期不是很理解的,请先看我之前的一片文章
http://menuz.iteye.com/blog/1255320


<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
	android:orientation="vertical" android:layout_width="fill_parent"
	android:layout_height="fill_parent">
	<Button android:layout_width="fill_parent"
		android:layout_height="wrap_content" android:id="@+id/cameraButton"
		android:text="拍照" />

	<SurfaceView android:id="@+id/surface_camera"
		android:layout_width="fill_parent" android:layout_height="10dip"
		android:layout_weight="1">
	</SurfaceView>
</LinearLayout>



<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
      package="com.busclient"
      android:versionCode="1"
      android:versionName="1.0">
    <uses-sdk android:minSdkVersion="7" />
    
    <uses-permission android:name="android.permission.CAMERA" /> <!-- 注意必须在application上面-->
    <application android:icon="@drawable/icon" android:label="@string/app_name">
    <uses-library android:name="com.google.android.maps" />
        <activity android:name=".Take2"
                  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.UPDATE_DEVICE_STATS"/>
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
</manifest>


package com.busclient;

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

import android.app.Activity;
import android.hardware.Camera;
import android.hardware.Camera.PictureCallback;
import android.os.Bundle;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;

public class Take2 extends Activity implements SurfaceHolder.Callback {
    private final static String TAG = "Take2";;

    private SurfaceView surfaceView;

    private SurfaceHolder surfaceHolder;

    private Camera mCam;

    private boolean hasStartPreview = false;

    private Button btnTakePicture;

    // Camera API:
    // Call release() to release the camera for use by other applications.
    // Applications should release the camera immediately in onPause() (and
    // re-open() it in onResume()).

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.takephoto);
        Log.d(TAG, "onCreate");

        // 取得surfaceView的引用,surface在surfaceView中展现
        // 当surfaceView可见时,surface会被创建,实现surfaceCreated进行特定操作
        surfaceView = (SurfaceView) findViewById(R.id.surface_camera);
        btnTakePicture = (Button) findViewById(R.id.cameraButton);
        // 注册按钮实现拍照
        btnTakePicture.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                if (mCam != null) {
                    // 调用mCam进行拍照
                    // param1 Camera.ShutterCallback 
                    // param2 Camera.PictureCallback raw 当原始图片数据获得时,会执行PictureCallback
                    // param3 Camera.PictureCallback compressed 当压缩数据获得时,会执行PictureCallback
                    mCam.takePicture(null, null, pictureCallBack);
                }
            }

        });

        // 要操作surface,只有通过surfaceHolder
        surfaceHolder = surfaceView.getHolder();
        surfaceHolder.addCallback(this);
        surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
    }

    private PictureCallback pictureCallBack = new Camera.PictureCallback() {

        @Override
        public void onPictureTaken(byte[] data, Camera camera) {
            if (mCam != null) {
                if (data != null) {
                    File f = new File("/data/data/com.busclient/picture1.jpg");
                    FileOutputStream fout = null;
                    try {
                        if (!f.exists())
                            f.createNewFile();
                        fout = new FileOutputStream(f);
                        fout.write(data);
                        fout.close();
                        Log.d(TAG, "write success");
                        
                        Thread.sleep(1500);
                    } catch (IOException e) {
                        e.printStackTrace();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    } finally {
                        try {
                            if (fout != null) {
                                fout.close();
                                fout = null;
                            }
                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                    }
                }
                finish();
            }
        }
    };

    // surface只能够由一个线程操作,一旦被操作,其他线程就无法操作surface
    @Override
    public void surfaceCreated(SurfaceHolder holder) {
        Log.d(TAG, "surfaceCreated");
        try {
            // 必须设置一个初始化的surfaceHolder,若没有surface(由holder操作surface),
            // 则camera无法启动预览 (就是一般打开照相机屏幕能够动态显示场景??描述的不够好)
            mCam.setPreviewDisplay(surfaceHolder);
        } catch (IOException e) {
            Log.d(TAG, "error");
            mCam.release();
            mCam = null;
        }
    }

    // 在surfaceCreated后调用,当surface发生变化也会触发该方法,这个方法
    // 一般至少被调用一次
    @Override
    public void surfaceChanged(SurfaceHolder holder, int format, int width,
            int height) {
        Log.d(TAG, "surfaceChanged");
        // 调用startPreview使预览surface可以更新,拍照
        // 必须启动预览,而startPreview必须在setPreviewDisplay(surfaceHolder)之后
        if (mCam != null && hasStartPreview == false) {

            mCam.startPreview();
            hasStartPreview = true;
        }
    }

    // 析构surface
    @Override
    public void surfaceDestroyed(SurfaceHolder holder) {
        Log.d(TAG, "surfaceDestroyed");
        // 活都被onPause抢去了
    }

    @Override
    protected void onDestroy() {
        Log.d(TAG, "onDestroy");
        super.onDestroy();
    }

    // onPause比surfaceDestroyed() 先调用
    @Override
    protected void onPause() {
        Log.d(TAG, "onPause");
        if (hasStartPreview) {
            mCam.stopPreview();
        }
        mCam.release();
        mCam = null;
        hasStartPreview = false;
        super.onPause();
    }

    @Override
    protected void onRestart() {
        Log.d(TAG, "onRestart");
        super.onRestart();
    }

    @Override
    protected void onResume() {
        Log.d(TAG, "onResume");
        if (mCam == null)
            mCam = Camera.open();
        super.onResume();
    }

    @Override
    protected void onStart() {
        Log.d(TAG, "onStart");
        super.onStart();
    }

    @Override
    protected void onStop() {
        Log.d(TAG, "onStop");
        super.onStop();
    }

}

2
0
分享到:
评论
3 楼 qhs1573 2012-11-13  
谢谢分享。
2 楼 Menuz 2011-11-30  
jd406 写道
能上传整个项目的代码么?

我这个是项目中抽取出来的。我觉得你按着我这个敲一遍代码印象会更深刻。
1 楼 jd406 2011-11-30  
能上传整个项目的代码么?

相关推荐

    Android 调用系统相机拍摄获取照片的两种方法实现实例

    在我们Android开发中经常需要做这个一个功能,调用系统相机拍照,然后获取拍摄的照片。下面是我总结的两种方法获取拍摄之后的照片,一种是通过Bundle来获取压缩过的照片,一种是通过SD卡获取的原图。 下面是演示代码...

    Android调用Camera实现拍照--github地址

    这是github的项目源码地址。Android Studio2.3.3调用系统的Camera实现拍照功能,并将照片保存到本地内存卡中

    android调用系统自带照相机拍照

    在Android开发中,调用系统...总的来说,Android调用系统自带相机拍照涉及权限管理、Intent启动相机应用、处理返回结果以及可能的自定义存储路径。理解这些知识点对于开发Android应用中涉及拍照功能的部分至关重要。

    android studio 调用相机拍照,选择相册照片

    在Android开发中,调用相机拍照和选择相册照片是常见的功能,这涉及到Android系统级别的交互和权限管理。本文将详细讲解如何在Android Studio中实现这两个功能,并将获取的图片进行存储。 首先,我们需要在...

    android调用其他Camera应用拍照

    在Android系统中,调用其他Camera应用拍照是一个常见的功能需求,...以上是关于"android调用其他Camera应用拍照"的基本介绍和实现方式,对于初学者和开发者来说,理解并掌握这些内容将有助于构建更丰富的Android应用。

    Android 调用相机拍照 添加照片水印

    以上就是Android调用相机拍照并添加照片水印的基本流程。在实际开发中,你可能还需要根据具体需求进行优化,例如添加图片裁剪功能、支持图片旋转、自定义水印样式等。记住,良好的用户体验和性能优化也是必不可少的...

    Android调用系统摄像头Camera.rar

    以上就是Android调用系统摄像头的主要知识点。通过理解并应用这些知识,你可以在你的应用中实现流畅的相机功能,让用户能够方便地拍照和录制视频。在实际开发中,应结合Android官方文档和相关示例代码进行深入学习和...

    Qt for Android 调用原生系统摄像头进行录像并保存输出

    本文将详细介绍如何使用Qt for Android调用原生系统的摄像头进行录像,并保存录制的视频输出。 首先,我们需要理解Qt中的多媒体模块,即`Q Multimedia`框架。这个模块提供了与多媒体内容交互的能力,包括音频、视频...

    delphi xe5 android 调用照相机摄像头拍照片camera

    在使用Delphi XE5开发Android应用程序时,调用照相机功能是常见的需求,以便让用户拍摄照片并集成到应用中。本示例着重讲解如何在Delphi XE5环境下,利用Android API来实现这一功能,无需额外的组件,只通过原生代码...

    Android下使用Camera硬件拍照Demo

    `Android下使用Camera硬件拍照Demo`就是这样一个示例项目,它展示了如何在Android应用中集成并使用系统相机硬件来捕捉图片。这个Demo通常包括设置相机参数、预览画面、拍照以及处理拍摄后的照片等关键步骤。 首先,...

    Android获取系统拍照程序发出的广播

    "Android获取系统拍照程序发出的广播"这个主题涉及到的是如何通过BroadcastReceiver来接收并处理系统相机应用拍照后的广播通知。下面将详细介绍这个过程,以及相关的知识点。 首先,Android系统在相机应用拍摄照片...

    delphi xe5 android 调用照相机获取拍的照片

    Delphi XE5 Android 调用照相机获取拍的照片 Delphi XE5 是一款功能强大且流行的开发环境,它提供了许多优秀的功能,包括对 Android 平台的支持。在 Android 平台上,Delphi XE5 提供了许多有用的组件和 API,允许...

    android调用前后置摄像头拍照

    以上就是Android调用前后置摄像头拍照的基本步骤。你可以根据实际需求进行扩展,比如添加闪光灯控制、设置拍照质量、裁剪图片等。这个`Android_Camera`压缩包文件可能包含了实现上述功能的完整代码示例,你可以参考...

    android手机相机自动连续拍照

    本文将深入探讨如何利用Android的Camera API或Camera2 API来创建一个能自动连续拍照的程序,并提供关于设置摄像头、调整参数以及保存照片到SD卡的相关知识。 1. **开启相机服务** 在Android中,相机功能通过Camera...

    android调用照相机拍照与选择本地照片功能

    在Android应用开发中,提供用户调用照相机拍照...以上就是关于“android调用照相机拍照与选择本地照片功能”的核心知识点,开发者在实现这些功能时,需要注意优化用户体验,合理管理文件,以及遵循Android的最佳实践。

    Android 调用系统相机拍照

    在Android应用开发中,调用系统相机拍照是一项常见的功能,用户可以使用手机摄像头捕捉图片,然后将图片数据返回到应用程序中。本篇文章将详细介绍如何在Android应用中实现这一功能,特别是静默拍照的方法。 首先,...

    android 调用系统照相机功能

    在Android应用开发中,调用系统照相机功能是常见的需求,允许用户拍摄照片或录制视频。下面我们将深入探讨如何实现这一功能。 首先,我们需要在AndroidManifest.xml文件中添加权限,以便应用可以访问摄像头: ```...

    Android下WebView中调用系统相机拍照范例

    在本文中,我们将深入探讨如何在WebView中调用系统的相机功能,允许用户拍照并返回照片的存储路径。这个功能对于构建混合型应用或者在网页中集成本地功能是非常实用的。 首先,我们需要在Android工程的`...

    Android 调用外接摄像头

    在Android平台上,调用外接摄像头是一项常见的...以上就是Android调用外接摄像头的基本流程和关键知识点,希望对你开发相关功能有所帮助。在实际项目中,可以结合提供的`android Demo`代码进一步理解和实践这些概念。

    android 调用照相机拍照

    在Android平台上,调用照相机拍照是常见的功能之一,它涉及到多媒体处理、用户交互以及硬件接口的使用。本文将深入探讨如何在Android应用中实现这一功能,并特别关注对焦优化。 首先,调用照相机拍照的基本流程是...

Global site tag (gtag.js) - Google Analytics