转至 (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。

  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,是个单例模式类。调用示例:

  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)),除保证比率外,还保证用户需要设置的尺寸宽度最小值。这个大家根据需要随便改。

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

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

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

    1. 常规方法,重写WebChromeClient 的 openFileChooser 方法 private class MyWebChromeClient extends WebChromeClie ...

  2. Android Camera开发系列(上)——Camera的基本调用与实现拍照功能以及获取拍照图片加载大图片

    Android Camera开发系列(上)--Camera的基本调用与实现拍照功能以及获取拍照图片加载大图片 最近也是在搞个破相机,兼容性那叫一个不忍直视啊,于是自己翻阅了一些基本的资料,自己实现了一 ...

  3. Android应用开发中关于this.context=context的理解

    在Android应用开发中,有的类里面需要声明一个Context的成员变量,然后还需要在该类的构造函数中加上this.context=context;这行代码.为什么要这么写呢?不写不行么? 先看下面 ...

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

    在Android开发中,定时器一般有以下3种实现方法: 原文地址http://www.360doc.com/content/12/0619/13/87000_219180978.shtml 一.采用H ...

  5. Android Camera开发系列(下)——自定义Camera实现拍照查看图片等功能

    Android Camera开发系列(下)--自定义Camera实现拍照查看图片等功能 Android Camera开发系列(上)--Camera的基本调用与实现拍照功能以及获取拍照图片加载大图片 上 ...

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

    Android应用开发中三种常见的图片压缩方法,分别是:质量压缩法.比例压缩法(根据路径获取图片并压缩)和比例压缩法(根据Bitmap图片压缩). 一.质量压缩法 private Bitmap com ...

  7. Android学习开发中如何保持API的兼容

    Android学习开发中如何保持API的兼容: 1,采用良好的设计思路 在设计过程中,如果能按照下面的方式来进行设计,会让这个API生命更长久 面向用例的设计,收集用户建议,把自己模拟成用户,保证AP ...

  8. [转]PHP开发中涉及到emoji表情的三种处理方法

    最近几个月做微信开发比较多,存储微信昵称必不可少,可这万恶的微信支持emoji表情做昵称,这就有点蛋疼了 一般Mysql表设计时,都是用UTF8字符集的.把带有emoji的昵称字段往里面insert一 ...

  9. Android Camera开发:周期性循环自动聚焦auto focus挂掉原因分析(preview is not enabled)

    参考:Android Camera开发:扫描二维码,周期性循环自动聚焦auto focus挂掉原因分析(preview is not enabled) 最近做Android人脸识别时,camera在自 ...

随机推荐

  1. Improving Performance【转】

    This section provides solutions to some performance problems, and describes configuration best pract ...

  2. git file mode change

    近期在做ffmpeg版本合并时发现,TortoiseGit的Check for Modifications的修改对话框中有未修改的问题,直接导出diff,会有类似下面的输出: compat/plan9 ...

  3. Python爬取猫眼top100排行榜数据【含多线程】

    # -*- coding: utf-8 -*- import requests from multiprocessing import Pool from requests.exceptions im ...

  4. nohup 后台启动程序,并输出到指定日志

    1.启动程序并输入到指定日志 nohup python manage.py runserver 0.0.0.0:9090 > /data/zyj/xadstat/xadstat.log 2&am ...

  5. 【Java】通用版URLConnection 带cookie下载PDF等资源文件

    /**** * 下载pdf文件 */ public static void downloadNet(String urlStr, String fileName, String savePath) t ...

  6. Vim中的寄存器

    # Vim中的寄存器 ### 文件名寄存器---- 粘贴文件名 `"%p"` ### 查看vim中的寄存器---- 查看寄存器 `reg` 或 `dis` ### 详细介绍---- ...

  7. Mybatis之工作原理

    1.Mybatis的架构 1.1 Mybatis的框架分层 1.2 MyBatis的实现原理 mybatis底层还是采用原生jdbc来对数据库进行操作的,它支持定制化 SQL.存储过程以及高级映射的优 ...

  8. C#学习笔记(24)——C#将PPT批量转为JPG(最简单的方法)

    说明(2017-8-1 11:15:46): 1. 哈哈,我就说微软肯定有自己的办法,把PPT转成图片. 2. 主要是要引入两个微软自己的程序集,vs里自带直接添加引用,注意一下版本,12.0是off ...

  9. JDBC插入数据超长时无法自动截断问题

    问题 JDBC操作MySQL数据库,当进行插入或更新操作的数据长度超过表字段的声明最大长度时,会报出以下错误,导致不能正常插入: 但是当直接在MySQL客户端操作时,发现确实可以的,只不过会自动对插入 ...

  10. 【Unity】使用AssetDatabase编辑器资源管理

    最近参考了各位大神的资源,初步学习了Unity的资源管理模式,包括在编辑器管理(使用AssetDatabase)和在运行时管理(使用Resources和AssetBundle).在此简单总结编辑器模式 ...