• Android图片处理:识别图像方向并显示


    在Android中使用ImageView显示图片的时候发现图片显示不正。方向偏了或者倒过来了。


    解决问题非常自然想到的分两步走:

    1、自己主动识别图像方向,计算旋转角度。

    2、对图像进行旋转并显示。


    一、识别图像方向

            首先在这里提一个概念EXIF(Exchangeable Image File Format,可交换图像文件),详细解释參见Wiki

    简而言之,Exif是一个标准,用于电子照相机(也包含手机、扫描器等)上。用来规范图片、声音、视屏以及它们的一些辅助标记格式。

    Exif支持的格式例如以下:

    图像 

      压缩图像文件:JPEG、DCT         

      非压缩图像文件:TIFF

          不支持:JPEG 2000、PNG、GIF  

    音频   

      RIFF、WAV

     


    Android提供了对JPEG格式图像Exif接口支持,能够读取JPEG文件metadata信息,參见ExifInterface.

            这些Metadata信息总的来说大致分为三类:日期时间、空间信息(经纬度、高度)、Camera信息(孔径、焦距、旋转角、曝光量等等)。


    二、图像旋转

    Android中提供了对Bitmap进行矩阵旋转的操作。參见Bitmap提供的静态createBitmap方法.

    public static Bitmap createBitmap (Bitmap source, int x, int y, int width, int height, Matrix m, boolean filter)

    Added in API level 1

    Returns an immutable bitmap from subset of the source bitmap, transformed by the optional matrix. The new bitmap may be the same object as source, or a copy may have been made. It is initialized with the same density as the original bitmap. If the source bitmap is immutable and the requested subset is the same as the source bitmap itself, then the source bitmap is returned and no new bitmap is created.

    Parameters
    sourceThe bitmap we are subsetting
    xThe x coordinate of the first pixel in source
    yThe y coordinate of the first pixel in source
    widthThe number of pixels in each row
    heightThe number of rows
    mOptional matrix to be applied to the pixels
    filtertrue if the source should be filtered. Only applies if the matrix contains more than just translation.
    Returns
    • A bitmap that represents the specified subset of source
    Throws
    IllegalArgumentExceptionif the x, y, width, height values are outside of the dimensions of the source bitmap.


    到此这两个问题理论上都攻克了,開始实际操作一下吧,參照下面代码。

    public class IOHelper {
    	
    	......
    	
    	/** 从给定路径载入图片*/
    	public static Bitmap loadBitmap(String imgpath) {
    		return BitmapFactory.decodeFile(imgpath);
    	}
    
    	
    	/** 从给定的路径载入图片,并指定是否自己主动旋转方向*/
    	public static Bitmap loadBitmap(String imgpath, boolean adjustOritation) {
    		if (!adjustOritation) {
    			return loadBitmap(imgpath);
    		} else {
    			Bitmap bm = loadBitmap(imgpath);
    			int digree = 0;
    			ExifInterface exif = null;
    			try {
    				exif = new ExifInterface(imgpath);
    			} catch (IOException e) {
    				e.printStackTrace();
    				exif = null;
    			}
    			if (exif != null) {
    				// 读取图片中相机方向信息
    				int ori = exif.getAttributeInt(ExifInterface.TAG_ORIENTATION,
    						ExifInterface.ORIENTATION_UNDEFINED);
    				// 计算旋转角度
    				switch (ori) {
    				case ExifInterface.ORIENTATION_ROTATE_90:
    					digree = 90;
    					break;
    				case ExifInterface.ORIENTATION_ROTATE_180:
    					digree = 180;
    					break;
    				case ExifInterface.ORIENTATION_ROTATE_270:
    					digree = 270;
    					break;
    				default:
    					digree = 0;
    					break;
    				}
    			}
    			if (digree != 0) {
    				// 旋转图片
    				Matrix m = new Matrix();
    				m.postRotate(digree);
    				bm = Bitmap.createBitmap(bm, 0, 0, bm.getWidth(),
    						bm.getHeight(), m, true);
    			}
    			return bm;
    		}
    	}
    		
    	......
    }
    


    ==========================================================================================

    欢迎增加我们的技术交流群:
    Android群: 66756039
    JavaEE群:  361579846 

  • 相关阅读:
    无线网路优化
    【设计模式】索引
    【c++算法】已序区间算法
    (转载)一个华为11年员工的国际惯例
    选择的结果
    明确价值体现
    只谈需求
    用block改写UIButton点击事件,block改写UIAlerView的代理
    UITableViewCell的三种加载方式
    如何从一个类的ViewController,如何获取一个UIView上的某种控件
  • 原文地址:https://www.cnblogs.com/lytwajue/p/6708416.html
Copyright © 2020-2023  润新知