浅析Android Camera开发中的三个尺寸和三种变形 (贡献一个自适配Picturesize和Previewsize的工具类)

转至 (http://blog.csdn.net/yanzi1225627/article/details/17652643)

经常听人问Camera开发中,各种变形问题,今天有空就在此梳理总结下。

三个尺寸:

1、Surfaceview的尺寸

Surfaceview是用来预览Camera的,当它全屏时就是Screen的大小。

2、Picturesize的尺寸

这是拍照后的PictureSize尺寸。

3、Previewsize的尺寸

这是预览时帧数据的尺寸。

三种变形:

1、预览画面的物体长宽失真。原因是Surfaceview和Previewsize的长宽比率不一致,就会导致预览画面上失真。因为camera在显示时会将预览帧数据缩放成Surfaceview大小,当比率不一致必然会物体变形。至于这个缩放算法可能不同手机会有区别。

2、拍照后照片上物体变形。

3、点击拍照瞬间,预览画面上会突然变形然后恢复到正常预览。

2、3两种变形都是因为Previewsize和Picturesize的长宽比率不一致所致。总之一句话,为了保证图片不是真,要保证预览Surfaceview、Previewsize、Picturesize的长宽比率要一直。如果Surfaceview是全屏的话,要获取屏幕长和宽得到比率。

为此我写了一个工具类,获得合适的Picturesize和Previewsize,名字为:MyCamPara.java。

[java] view plaincopyprint?

  1. package org.yanzi.util;
  2. import java.util.Collections;
  3. import java.util.Comparator;
  4. import java.util.List;
  5. import android.hardware.Camera;
  6. import android.hardware.Camera.Size;
  7. import android.util.Log;
  8. public class MyCamPara {
  9. private static final String tag = "yan";
  10. private CameraSizeComparator sizeComparator = new CameraSizeComparator();
  11. private static MyCamPara myCamPara = null;
  12. private MyCamPara(){
  13. }
  14. public static MyCamPara getInstance(){
  15. if(myCamPara == null){
  16. myCamPara = new MyCamPara();
  17. return myCamPara;
  18. }
  19. else{
  20. return myCamPara;
  21. }
  22. }
  23. public  Size getPreviewSize(List<Camera.Size> list, int th){
  24. Collections.sort(list, sizeComparator);
  25. int i = 0;
  26. for(Size s:list){
  27. if((s.width > th) && equalRate(s, 1.33f)){
  28. Log.i(tag, "最终设置预览尺寸:w = " + s.width + "h = " + s.height);
  29. break;
  30. }
  31. i++;
  32. }
  33. return list.get(i);
  34. }
  35. public Size getPictureSize(List<Camera.Size> list, int th){
  36. Collections.sort(list, sizeComparator);
  37. int i = 0;
  38. for(Size s:list){
  39. if((s.width > th) && equalRate(s, 1.33f)){
  40. Log.i(tag, "最终设置图片尺寸:w = " + s.width + "h = " + s.height);
  41. break;
  42. }
  43. i++;
  44. }
  45. return list.get(i);
  46. }
  47. public boolean equalRate(Size s, float rate){
  48. float r = (float)(s.width)/(float)(s.height);
  49. if(Math.abs(r - rate) <= 0.2)
  50. {
  51. return true;
  52. }
  53. else{
  54. return false;
  55. }
  56. }
  57. public  class CameraSizeComparator implements Comparator<Camera.Size>{
  58. //按升序排列
  59. public int compare(Size lhs, Size rhs) {
  60. // TODO Auto-generated method stub
  61. if(lhs.width == rhs.width){
  62. return 0;
  63. }
  64. else if(lhs.width > rhs.width){
  65. return 1;
  66. }
  67. else{
  68. return -1;
  69. }
  70. }
  71. }
  72. }

对上面这个工具类注释如下:

1,是个单例模式类。调用示例:

[java] view plaincopyprint?

  1. Size pictureS = MyCamPara.getInstance().getPictureSize(pictureSizes, 800);
  2. myParam.setPictureSize(pictureS.width, pictureS.height);

2,程序首先对预览尺寸的list进行升序排序,因为实际中发现,有的手机提供的是升序有的是降序。

3,通过equalRate(Size s, float rate)保证Size的长宽比率。一般而言这个比率为1.333/1.7777即通常说的4:3和16:9比率。

4、在getPreviewSize()函数里增加判断if((s.width > th) && equalRate(s, 1.33f)),除保证比率外,还保证用户需要设置的尺寸宽度最小值。这个大家根据需要随便改。

如果您觉得笔者在认真的写博客,请为我投上一票,谢谢大家。

时间: 2024-08-02 11:51:51

浅析Android Camera开发中的三个尺寸和三种变形 (贡献一个自适配Picturesize和Previewsize的工具类)的相关文章

Android应用开发中webview上传文件的几种思路

1. 常规方法,重写WebChromeClient 的 openFileChooser 方法 private class MyWebChromeClient extends WebChromeClient { // For Android 3.0+ public void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType) { if (mUploadMessage != null) return; mUploadMe

Android Camera开发之基础知识篇

概述 Android框架支持设备的相机拍照和录像功能,你的应用可以直接调用系统的Camera应用来拍照或者录像(比如微信拍照),当然也可以利用Android系统提供的API开发一个Camera应用来实现相机拍照和录像功能(比如市面上流行的360相机).此篇文章主要记录相机开发有关的基础知识,以及带着自己的理解翻译Camera官方文档,如有翻译不恰当支出,还请指出改正.当然我会开一个有关相机开发的一个系列,该系列主要内容包括如下: 相机基本预览拍照功能. 实现相机的Flash,Hdr,滤镜,前后摄

玩转Android Camera开发(五):基于Google自带算法实时检测人脸并绘制人脸框(网络首发,附完整demo)

本文主要介绍使用Google自带的FaceDetectionListener进行人脸检测,并将检测到的人脸用矩形框绘制出来.本文代码基于PlayCameraV1.0.0,在Camera的open和preview流程上进行了改动.原先是放在单独线程里,这次我又把它放到Surfaceview的生命周期里进行打开和开预览. 首先要反省下,去年就推出了静态图片的人脸检测demo,当时许诺一周内推出Camera预览实时检测并绘制的demo,结果拖到现在才整.哎,屌丝一天又一天,蹉跎啊.在demo制作过程中

玩转Android Camera开发(四):预览界面四周暗中间亮,只拍摄矩形区域图片(附完整源码)

杂家前文曾写过一篇关于只拍摄特定区域图片的demo,只是比较简陋,在坐标的换算上不是很严谨,而且没有完成预览界面四周暗中间亮的效果,深以为憾,今天把这个补齐了. 在上代码之前首先交代下,这里面存在着换算的两种模式.第一种,是以屏幕上的矩形区域为基准进行换算.举个例子,屏幕中间一个 矩形框为100dip*100dip.这里一定要使用dip为单位,否则在不同的手机上屏幕呈现的矩形框大小不一样.先将这个dip换算成px,然后根据屏幕的宽和高的像素计算出矩形区域,传给Surfaceview上铺的一层Vi

Android实际开发中的bug总结与解决方法(一)

                                                                             Android实际开发中的bug总结与解决方法(一) Android开发中有很多bug,我们是完全可以在线下避免的,不要等到线上报的BUG的再去修复.下面是我在实际开发中遇到过的bug和解决方法. BUG 1: java.lang.RuntimeException: Unable to start activity ComponentInfo

玩转Android Camera开发(一):Surfaceview预览Camera,基础拍照功能完整demo

杂家前文是在2012年的除夕之夜仓促完成,后来很多人指出了一些问题,琐事缠身一直没有进行升级.后来随着我自己的使用,越来越发现不出个升级版的demo是不行了.有时候就连我自己用这个demo测一些性能.功能点,用着都不顺手.当初代码是在linux下写的,弄到windows里下全是乱码.还要自己改几分钟才能改好.另外,很多人说不能正常预览,原因是我在布局里把Surfaceview的尺寸写死了.再有就是initCamera()的时候设参数失败,直接黑屏退出,原因也是我把预览尺寸和照片尺寸写死了.再有就

Android应用开发中三种常见的图片压缩方法

Android应用开发中三种常见的图片压缩方法,分别是:质量压缩法.比例压缩法(根据路径获取图片并压缩)和比例压缩法(根据Bitmap图片压缩). 一.质量压缩法 private Bitmap compressImage(Bitmap image) { ByteArrayOutputStream baos = new ByteArrayOutputStream(); image.compress(Bitmap.CompressFormat.JPEG, 100, baos);//质量压缩方法,这里

android游戏开发中图形绘制:Canvas和Paint的使用

android游戏开发中,使用android.graphics中的类来绘制2D向量图和文字. 一 画布Canvas 在Android中的绘图应该继承View组件,并重写它的onDraw(Canvas canvas)方法. Canvas代表指定View上的画布,常用方法如图: 二 画刷Paint Paint代表Canvas上的画刷,主要用于绘制风格,包括画刷颜色.画刷笔触粗细.填充风格等. 大体上可以分为两类,一类与图形绘制相关,一类与文本绘制相关. 常用方法如图: 三 路径Path Path表示

在Android开发中,定时器一般有以下3种实现方法

在Android开发中,定时器一般有以下3种实现方法: 原文地址http://www.360doc.com/content/12/0619/13/87000_219180978.shtml 一.采用Handler与线程的sleep(long)方法二.采用Handler的postDelayed(Runnable, long)方法三.采用Handler与timer及TimerTask结合的方法 下面逐一介绍: 一.采用Handle与线程的sleep(long)方法 Handler主要用来处理接受到的