您好!欢迎来到源码码网

Android Camera相机以及相机程序开发实例

  • 源码教程
  • 来源:源码码网
  • 编辑:admin
  • 时间:2021-01-14 20:32
  • 阅读:388

在之前的教程中介绍过拍照程序,是通过 Intent调用 Android 系统提供的照相机程序实现的。

Android SDK 提供了直接操作移动设备摄像头的 android.hardware.Camera 类,通过该类的相关 API,可以直接操作 Android 手机中的摄像头,以方便开发自己的拍照程序。

使用 Camera 类访问移动设备的摄像头,需要在应用程序的 AndroidManifest.xml 文件中做以下声明:

<uses-permission android:name="android.permission.CAMERA" />
<uses-feature android:name="android.hardware.camera" />


使用 Camera 类进行拍照的步骤如下:

1)使用 Camera.open() 方法获取 Camera 对象实例。

2)使用 Camera.getParameters() 方法获取当前相机的相关设置。

3)根据需要使用 Camera.setParameters() 方法设置相机的相关参数。

4)根据需要使用 Camera.setDisplayOrientation() 设置相机正向。

5)使用 Camera.setPreviewDisplay() 方法为相机设置一个用于显示相机图像的 Surface。

6)使用 Camera.startPreview() 启动预览。

7)使用 Camera.takePicture() 方法进行拍照。

8)进行拍照后,预览视图会停止。使用 Camera.startPreview() 方法重新启动预览。

9)使用 Camera.stopPreview() 停止预览。

10)使用 Camera.release() 方法释放相机对象。应该在应用程序的 onPause() 方法中释放相机对象,在 onResume() 方法中重新打开相机对象。

实例 MyCameraDemo 演示了使用 Camera 类进行拍照的过程,该应用程序的运行效果如图 1 所示。

MyCameraDemo运行结果

图 1  MyCameraDemo运行结果

该视图所使用布局文件 main.xml 的代码如下:


  1. <?xml version="1.0" encoding="utf-8"?>

  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

  3. android:layout_width="fill_parent"

  4. android:layout_height="fill_parent"

  5. android:orientation="vertical">


  6. <TextView

  7. android:layout_width="fill_parent"

  8. android:layout_height="wrap_content"

  9. android:text="@string/hello" />


  10. <SurfaceView

  11. android:id="@+id/surfaceView1"

  12. android:layout_width="fill_parent"

  13. android:layout_height="wrap_content"

  14. android:layout_weight="0.58" />


  15. <LinearLayout

  16. android:id="@+id/linearLayout1"

  17. android:layout_width="match_parent"

  18. android:layout_height="wrap_content"

  19. android:gravity="center">


  20. <Button

  21. android:id="@+id/button1"

  22. android:layout_width="wrap_content"

  23. android:layout_height="wrap_content"

  24. android:text="@string/opBtn" />


  25. <Button

  26. android:id="@+id/button2"

  27. android:layout_width="wrap_content"

  28. android:layout_height="wrap_content"

  29. android:text="@string/play" />


  30. <Button

  31. android:id="@+id/button3"

  32. android:layout_width="wrap_content"

  33. android:layout_height="wrap_content"

  34. android:text="@string/cloBtn" />



  35. </LinearLayout>



  36. </LinearLayout>

实例 MyCameraDemo 使用到的资源文件 string.xml 的代码如下:

  1. <resources>

  2. <string name="hello">使用Android.hardware.Camera</string>

  3. <string name="app_name">MyCameraDemo</string>

  4. <string name="opBtn">打开摄像头</string>

  5. <string name="play">拍摄</string>

  6. <string name="cloBtn">关闭摄像头</string>

  7. </resources>

由于实例 MyCameraDemo 中涉及将拍摄的照片保存到 SD 卡中的功能,因此需要在该工程的 AndroidManifest.xml 文件中声明相应权限。该文件内容如下:


  1. <?xml version="1.0" encoding="utf-8"?>

  2. <manifest xmlns:android="http://schemas.android.com/apk/res/android"

  3. package="introduction.android.mycamerademo"

  4. android:versionCode="1"

  5. android:versionName="1.0">


  6. <uses-sdk android:minSdkVersion="14" />

  7. <uses-feature android:name="android.hardware.camera" />


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

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


  10. <application

  11. android:allowBackup="true"

  12. android:icon="@mipmap/ic_launcher"

  13. android:label="@string/app_name"

  14. android:roundIcon="@mipmap/ic_launcher_round"

  15. android:supportsRtl="true"

  16. android:theme="@style/AppTheme">

  17. <activity android:name=".MainActivity">

  18. <intent-filter>

  19. <action android:name="android.intent.action.MAIN" />


  20. <category android:name="android.intent.category.LAUNCHER" />

  21. </intent-filter>

  22. </activity>

  23. </application>


  24. </manifest>

实例 MyCameraDemo 的主 Activity 为 MainActivity,其代码如下:


  1. package introduction.android.mycamerademo;


  2. import java.io.BufferedOutputStream;

  3. import java.io.File;


  4. import java.io.FileNotFoundException;

  5. import java.io.FileOutputStream;

  6. import java.io.IOException;


  7. import android.app.Activity;

  8. import android.graphics.Bitmap;

  9. import android.graphics.BitmapFactory;

  10. import android.graphics.PixelFormat;

  11. import android.hardware.Camera;

  12. import android.hardware.Camera.Parameters;

  13. import android.hardware.Camera.PictureCallback;

  14. import android.os.Bundle;

  15. import android.util.Log;

  16. import android.view.SurfaceHolder;

  17. import android.view.SurfaceView;

  18. import android.view.View;

  19. import android.view.View.OnClickListener;

  20. import android.widget.Button;


  21. public class MainActivity extends Activity {

  22. private Button opbtn;

  23. private Button playbtn;

  24. private Button clobtn;

  25. private SurfaceView surfaceView;

  26. private SurfaceHolder surfaceHolder;

  27. private Camera camera;

  28. private int previewWidth = 320;

  29. private int previewHeight = 240;


  30. protected String filepath = "/sdcard/mypicture.jpg";


  31. /**

  32.     * Called when the activity is first created.

  33.     */

  34. @Override

  35. public void onCreate(Bundle savedInstanceState) {

  36. super.onCreate(savedInstanceState);

  37. setContentView(R.layout.activity_main);

  38. opbtn = (Button) this.findViewById(R.id.button1);

  39. playbtn = (Button) this.findViewById(R.id.button2);

  40. clobtn = (Button) this.findViewById(R.id.button3);

  41. surfaceView = (SurfaceView) this.findViewById(R.id.surfaceView1);

  42. surfaceHolder = surfaceView.getHolder();

  43. surfaceHolder.addCallback(new SurfaceHolder.Callback() {


  44. @Override

  45. public void surfaceDestroyed(SurfaceHolder holder) {

  46. // TODO Auto-generated method stub

  47. Log.i("camera", "surface destroyed.");

  48. }


  49. @Override

  50. public void surfaceCreated(SurfaceHolder holder) {

  51. // TODO Auto-generated method stub

  52. Log.i("camera", "surface destroyed");

  53. }


  54. @Override

  55. public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {

  56. // TODO Auto-generated method stub

  57. Log.i("camera", "surface changed.");

  58. }

  59. });

  60. opbtn.setOnClickListener(new OnClickListener() {

  61. //开启摄像头

  62. @Override

  63. public void onClick(View argO) {

  64. // TODO Auto-generated method stub

  65. openCamera();

  66. }

  67. });

  68. playbtn.setOnClickListener(new OnClickListener() {

  69. //拍照

  70. @Override

  71. public void onClick(View v) {

  72. // TODO Auto-generated method stub

  73. takePicture();

  74. }

  75. });

  76. clobtn.setOnClickListener(new OnClickListener() {

  77. //关闭摄像头

  78. @Override

  79. public void onClick(View v) {

  80. // TODO Auto-generated method stub

  81. closeCamera();

  82. }

  83. });

  84. }


  85. protected void closeCamera() {

  86. // TODO Auto-generated method stub

  87. camera.stopPreview();

  88. camera.release();

  89. camera = null;

  90. }


  91. protected void takePicture() {

  92. // TODO Auto-generated method stub

  93. if (checkSDCard()) {

  94. camera.takePicture(null, null, jpeg);

  95. try {

  96. Thread.sleep(1000);

  97. } catch (InterruptedException e) {

  98. // TODO Auto-generated catch block

  99. e.printStackTrace();

  100. }

  101. camera.startPreview();

  102. } else {

  103. Log.e("camera", "SD CARD not exist.");

  104. return;

  105. }

  106. }


  107. private void openCamera() {

  108. // TODO Auto-generated method stub

  109. try {

  110. camera = Camera.open(); // attempt to get a Camera instance

  111. } catch (Exception e) {

  112. // Camera is not available (in use or does not exist)

  113. Log.e("camera", "open camera error!");

  114. e.printStackTrace();

  115. return;

  116. }

  117. Parameters params = camera.getParameters();

  118. params.setPreviewSize(previewWidth, previewHeight);

  119. params.setPictureFormat(PixelFormat.JPEG);

  120. params.setPictureSize(previewWidth, previewHeight);

  121. camera.setParameters(params);

  122. try {

  123. camera.setPreviewDisplay(surfaceHolder);

  124. } catch (IOException e) {

  125. // TODO Auto-generated catch block

  126. Log.e("camera", "preview failed.");

  127. e.printStackTrace();

  128. }

  129. camera.startPreview();

  130. }


  131. private PictureCallback jpeg = new PictureCallback() {

  132. @Override

  133. public void onPictureTaken(byte[] data, Camera camera) {

  134. // TODO Auto-generated method stub

  135. Bitmap bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);

  136. File pictureFile = new File(filepath);

  137. if (pictureFile == null) {

  138. Log.d("camera",

  139. "Error creating media file, check storage permissions");

  140. return;

  141. }

  142. try {

  143. //将拍摄的照片写入SD卡中

  144. FileOutputStream fos = new FileOutputStream(pictureFile);

  145. BufferedOutputStream bos = new BufferedOutputStream(fos);

  146. bitmap.compress(Bitmap.CompressFormat.JPEG, 80, bos);

  147. bos.flush();

  148. bos.close();

  149. fos.close();

  150. Log.i("camera", "jpg file saved.");

  151. } catch (FileNotFoundException e) {

  152. Log.d("camera", "File not found: " + e.getMessage());

  153. } catch (IOException e) {

  154. Log.d("camera", "Error accessing file: " + e.getMessage());

  155. }

  156. }

  157. };


  158. private boolean checkSDCard() {

  159. // 判断SD存储卡是否存在

  160. if (android.os.Environment.getExternalStorageState().equals

  161. (android.os.Environment.MEDIA_MOUNTED)) {

  162. return true;

  163. } else {

  164. return false;

  165. }

  166. }

  167. }


其中,openCamera() 方法用于打开当前设备的相机,并通过:

  1. Parameters params=camera.getParameters();

  2. params.setPreviewSize(previewWidth, previewHeight);

  3. params.setPictureFormat(PixelFormat.JPEG);

  4. params.setPictureSize(previewWidth, previewHeight);

  5. camera.setParameters(params);

设置相机的相关参数,以用于照片拍摄。

通过以下代码:

surfaceView=(SurfaceView)this.findViewById(R.id.surfaceView1);
surfaceHolder=surfaceView.getHolder();
camera.setPreviewDisplay(surfaceHolder);

将布局中的 SurfaceView 组件设置为相机的预览窗口。

由于在拍摄照片后,预览视图会自动停止预览而显示拍摄的照片,因此在本例中人为将照片显示时间设定为 1s,然后重新启动预览。相关代码如下:

  1. camera.takePicture(null, null, jpeg);

  2. try {

  3. Thread.sleep(1000);

  4. } catch (InterruptedException e) {

  5. // TODO Auto-generated catch block

  6. e.printStackTrace();

  7. }

  8. camera.startPreview();


特别声明:
1、如无特殊说明,内容均为本站原创发布,转载请注明出处;
2、部分转载文章已注明出处,转载目的为学习和交流,如有侵犯,请联系客服删除;
3、编辑非《源码码网》的文章均由用户编辑发布,不代表本站立场,如涉及侵犯,请联系删除;
全部评论(0)
推荐阅读
  • bootstrap ui框架能用在uniapp中吗?
  • bootstrap ui框架能用在uniapp中吗?
  • BootstrapUI框架通常是前端开发中的一种工具,它提供了一套预定义的CSS样式和组件,用于快速构建响应式布局的网页。然而,UniApp是一个使用Vue.js开发跨平台应用的框架,它可以用来开发iOS、Android、以及各种小程序和H5应用。
  • 互动社区
  • 来源:源码码网
  • 编辑:热度建站
  • 时间:2024-04-12 00:04
  • 阅读:186
  • css实现banner图由中心点动态放大效果
  • css实现banner图由中心点动态放大效果
  • 在日常的网页设计中,为了让网页增加一定的特效以达到交互的目的,我们尝尝会在网页中使用一些动画效果。今天来说说实现banner图由中心点动态放大效果,实现这个效果需要用到css中的动画:animation​和关键帧:@keyframes,具体示例如下:
  • 源码教程
  • 来源:源码码网
  • 编辑:源码码网
  • 时间:2024-04-11 18:52
  • 阅读:200
  • countUp.js实现鼠标滑动到某个位置数字自动滚动增加的效果
  • countUp.js实现鼠标滑动到某个位置数字自动滚动增加的效果
  • 在网页开发中为了提升网页的交互效果,经常会用到使用js给网页增加一定的特效,下边就来说说使用js实现鼠标滑动到某个位置数字自动滚动增加的效果。其实这种效果有很多中解决办法,自己也可以去写,下边我们借助countUp.js来实现,关于这个js文件,我放在末尾:
  • 源码教程
  • 来源:源码码网
  • 编辑:源码码网
  • 时间:2024-04-08 09:20
  • 阅读:275
  • 响应式网页设计思路及注意事项
  • 响应式网页设计思路及注意事项
  • 一、什么是响应式网页响应式网页设计就是让网页具有根据设备类型应用CSS样式的能力。设计:设想、计划。设计就是把想法实现。网页设计:按照一定的设计思路布局网页内容。传统网页设计:都是针对PC端浏览器而设计的,不具备查询设备的能力,更不能对多种访问设备做出响应。传统网页设计的弊端:在移动互联网时代,传统的网页设计不适合多屏幕时代。响应式网页设计应运而生。响应式网页设计是一种设计网页的思想/方法。响应:指让我们的网页能够自动查询用户的访问设备
  • 源码教程
  • 来源:源码码网
  • 编辑:源码码网
  • 时间:2024-04-02 11:24
  • 阅读:182
  • css中rel的属性值都有哪些,分别代表什么意思
  • css中rel的属性值都有哪些,分别代表什么意思
  • 在HTML中,元素的rel属性用于定义当前文档与被链接文档之间的关系。这个属性在CSS的上下文中经常与样式表关联,但rel属性的用途远不止于此。以下是一些常见的rel属性值及其意义:1、stylesheet:表示被链接的文档是一个样式表。这通常用于链接CSS文件。
  • 源码教程
  • 来源:源码码网
  • 编辑:源码码网
  • 时间:2024-03-28 12:28
  • 阅读:311
联系客服
源码代售 源码咨询 素材咨询 联系客服
029-84538663
手机版

扫一扫进手机版
返回顶部