博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
iOS开发中关于UIImage的知识点总结
阅读量:6035 次
发布时间:2019-06-20

本文共 14982 字,大约阅读时间需要 49 分钟。

UIImage是iOS中层级比较高的一个用来加载和绘制图像的一个类,更底层的类还有 CGImage,以及iOS5.0以后新增加的CIImage。今天我们主要聊一聊UIImage的三个属性: imageOrientation, size, scale,几个初始化的方法: imageNamed,imageWithContentsOfFile,以及绘制Image的几个draw开头的方法。AD:51CTO 网+ 第十二期沙龙:大话数据之美_如何用数据驱动用户体验UIImage是iOS中层级比较高的一个用来加载和绘制图像的一个类,更底层的类还有 CGImage,以及iOS5.0以后新增加的CIImage。今天我们主要聊一聊UIImage的三个属性: imageOrientation, size, scale,几个初始化的方法: imageNamed,imageWithContentsOfFile,以及绘制Image的几个draw开头的方法。一、UIImage的size,scale属性先想一个问题“一个图像的尺寸到底是多大呢?”第一反应可能就是image.size,恭喜你答错了,正确的答案是图像的实际的尺寸(像 素)等于image.size乘以image.scale。如果做过界面贴图的话你可能经常会需要准备至少两套图,一套1倍图,一套图已@2x命名的二倍 图。这样当我们的程序运行在retina屏幕的时候系统就会自动的去加载@2x的图片,它的size将和一倍图加载进来的size相等,但是scale却 置为2,这点大家可以做个简单的小测试验证一下。然我们再深入一点儿为什么不直接加载到成二倍的尺寸呢,原因很简单因为我们在界面布局中逻辑坐标系中的 (单位是point),而实际的绘制都是在设备坐标系(单位是pixel)进行的,系统会自动帮我们完成从point到pixel之间的转化。其实这个比 例也就刚好和UIScreen中的scale对应,这样整条scale的线就可以串通了。二、UIImage的几种初始化方法的对比1、imageNamed:方法imageNamed:是UIImage的一个类方法,它做的事情比我们看到的要稍微多一些。它的加载流程如下:a. 系统回去检查系统缓存中是否存在该名字的图像,如果存在则直接返回。b. 如果系统缓存中不存在该名字的图像,则会先加载到缓存中,在返回该对象。观察上面的操作我们发现系统会缓存我们使用imageNamed:方法加载的图像时候,系统会自动帮我们缓存。这种机制适合于那种频繁用到界面贴图累的加载,但如果我们需要短时间内频繁的加载一些一次性的图像的话,最好不要使用这种方法。2、imageWithContentsOfFile:和initWithContentsOfFile:方法这两个方法跟前一个方法一样都是完成从文件加载图像的功能。但是不会经过系统缓存,直接从文件系统中加载并返回。顺便提一下,当收到内存警告的时候,系统可能会将UIImage内部的存储图像的内存释放,下一次需要绘制的时候会重新去加载。3、imageWithCGImage:scale:orientation:方法该方面使用一个CGImageRef创建UIImage,在创建时还可以指定方法倍数以及旋转方向。当scale设置为1的时候,新创建的图像将和原图像尺寸一摸一样,而orientaion则可以指定新的图像的绘制方向。三、UIImage的imageOrientation属性UIImage有一个imageOrientation的属性,主要作用是控制image的绘制方向,共有以下8中方向:    typedef NS_ENUM(NSInteger, UIImageOrientation) {         UIImageOrientationUp,            // default orientation            UIImageOrientationDown,          // 180 deg rotation                UIImageOrientationLeft,          // 90 deg CCW      (编程发现官方文档中,left和right图像标反了,此处更正过来)         UIImageOrientationRight,         // 90 deg CW            UIImageOrientationUpMirrored,    // as above but image mirrored along other axis. horizontal flip           UIImageOrientationDownMirrored,  // horizontal flip         UIImageOrientationLeftMirrored,  // vertical flip          UIImageOrientationRightMirrored, // vertical flip      }; 默认的方向是UIImageOrientationUp,这8种方向对应的绘制方如上面所示。我 们在日常使用中经常会碰到把iPhone相册中的照片导入到windows中,发现方向不对的问题就是与这个属性有关,因为导出照片的时候,写exif中 的方向信息时候没有考虑该方向的原因。既然这个属性可以控制image的绘制方向,那我们能不能通过改过这个属性来完成UIImage的旋转和翻转呢?带 着这个问题我们继续往下看。四、UIImage的几个draw方法UIImage的几个draw方法是用来绘制图像的利器,为什么这样说呢?因为它们在绘制图 像的时候会考虑当前图像的方向,即根据的imageOrientation绘制出不同的方向。由于图像是绘制在当前context中的,它同时还会考虑到 当前context的transform的变化。利于这两点我们就可以玩转图像的旋转和翻转了。搜索了一些,目前网上大部分图像旋转都是通过创建CGBitmapContext,然后根据图像方向设置context的transform来实现的,这种方法要求对整个矩阵变化的过程都非常清楚,一个参数设置不多,出来的结果就会有问题。下面我介绍一种实现起来简单方便的图像旋转方法,这种方法主要就是利用imageWithCGImage:scale:orientation:方法,指定不同的orientation来完成所需要的功能,先举个简单的例子:假设一副图片显示为 iOS开发中关于UIImage的知识点 - 第1张 | IT江湖,我们要向左旋转90°,那么转过之后应该就会显示为iOS开发中关于UIImage的知识点 - 第2张 | IT江湖,即将原图从orientationUP转到orientationLeft即可。以此类推为不同的方向旋转,只需要注意看R的显示即可,这样整个旋转和翻转的实现过程中完全可以不用考虑Transform那些东西,是不是很简单。下面是图像旋转和翻转的完整代码:    //     //  UIImage+Rotate_Flip.h     //  SvImageEdit     //     //  Created by  maple on 5/14/13.     //  Copyright (c) 2013 smileEvday. All rights reserved.     //     //           #import 
@interface UIImage (Rotate_Flip) /* * @brief rotate image 90 withClockWise */ - (UIImage*)rotate90Clockwise; /* * @brief rotate image 90 counterClockwise */ - (UIImage*)rotate90CounterClockwise; /* * @brief rotate image 180 degree */ - (UIImage*)rotate180; /* * @brief rotate image to default orientation */ - (UIImage*)rotateImageToOrientationUp; /* * @brief flip horizontal */ - (UIImage*)flipHorizontal; /* * @brief flip vertical */ - (UIImage*)flipVertical; /* * @brief flip horizontal and vertical */ - (UIImage*)flipAll; @end UIImage+Rotate_Flip.h // // UIImage+Rotate_Flip.m // SvImageEdit // // Created by maple on 5/14/13. // Copyright (c) 2013 smileEvday. All rights reserved. // #import "UIImage+Rotate_Flip.h" @implementation UIImage (Rotate_Flip) /* * @brief rotate image 90 with CounterClockWise */ - (UIImage*)rotate90CounterClockwise { UIImage *image = nil; switch (self.imageOrientation) { case UIImageOrientationUp: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeft]; break; } case UIImageOrientationDown: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRight]; break; } case UIImageOrientationLeft: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDown]; break; } case UIImageOrientationRight: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUp]; break; } case UIImageOrientationUpMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRightMirrored]; break; } case UIImageOrientationDownMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeftMirrored]; break; } case UIImageOrientationLeftMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUpMirrored]; break; } case UIImageOrientationRightMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDownMirrored]; break; } default: break; } return image; } /* * @brief rotate image 90 with Clockwise */ - (UIImage*)rotate90Clockwise { UIImage *image = nil; switch (self.imageOrientation) { case UIImageOrientationUp: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRight]; break; } case UIImageOrientationDown: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeft]; break; } case UIImageOrientationLeft: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUp]; break; } case UIImageOrientationRight: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDown]; break; } case UIImageOrientationUpMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeftMirrored]; break; } case UIImageOrientationDownMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRightMirrored]; break; } case UIImageOrientationLeftMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDownMirrored]; break; } case UIImageOrientationRightMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUpMirrored]; break; } default: break; } return image; } /* * @brief rotate image 180 degree */ - (UIImage*)rotate180 { UIImage *image = nil; switch (self.imageOrientation) { case UIImageOrientationUp: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDown]; break; } case UIImageOrientationDown: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUp]; break; } case UIImageOrientationLeft: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRight]; break; } case UIImageOrientationRight: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeft]; break; } case UIImageOrientationUpMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDownMirrored]; break; } case UIImageOrientationDownMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUpMirrored]; break; } case UIImageOrientationLeftMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRightMirrored]; break; } case UIImageOrientationRightMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeftMirrored]; break; } default: break; } return image; } /* * @brief rotate image to default orientation */ - (UIImage*)rotateImageToOrientationUp { CGSize size = CGSizeMake(self.size.width * self.scale, self.size.height * self.scale); UIGraphicsBeginImageContext(size); CGContextRef context = UIGraphicsGetCurrentContext(); CGContextClearRect(context, CGRectMake(0, 0, size.width, size.height)); [self drawInRect:CGRectMake(0, 0, size.width, size.height)]; UIImage *image = UIGraphicsGetImageFromCurrentImageContext(); UIGraphicsEndImageContext(); return image; } /* * @brief flip horizontal */ - (UIImage*)flipHorizontal { UIImage *image = nil; switch (self.imageOrientation) { case UIImageOrientationUp: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUpMirrored]; break; } case UIImageOrientationDown: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDownMirrored]; break; } case UIImageOrientationLeft: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRightMirrored]; break; } case UIImageOrientationRight: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeftMirrored]; break; } case UIImageOrientationUpMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUp]; break; } case UIImageOrientationDownMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDown]; break; } case UIImageOrientationLeftMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRight]; break; } case UIImageOrientationRightMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeft]; break; } default: break; } return image; } /* * @brief flip vertical */ - (UIImage*)flipVertical { UIImage *image = nil; switch (self.imageOrientation) { case UIImageOrientationUp: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDownMirrored]; break; } case UIImageOrientationDown: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUpMirrored]; break; } case UIImageOrientationLeft: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeftMirrored]; break; } case UIImageOrientationRight: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRightMirrored]; break; } case UIImageOrientationUpMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationDown]; break; } case UIImageOrientationDownMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationUp]; break; } case UIImageOrientationLeftMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationLeft]; break; } case UIImageOrientationRightMirrored: { image = [UIImage imageWithCGImage:self.CGImage scale:1 orientation:UIImageOrientationRight]; break; } default: break; } return image; } /* * @brief flip horizontal and vertical */ - (UIImage*)flipAll { return [self rotate180]; } @end UIImage+Rotate_Flip.m 以上只是实现了图像的顺时针90°,逆时针90°,180°旋转,以及水平翻转,数值翻转等。至 于任意角度旋转怎么实现?其实也很简单,留着给大家思考吧。虽然我们可以通过orientation这种方法简单的完成图像旋转,但是如果有时间的话还是 建议大家尽量的看一下那种通过transform来完成旋转的代码,你会彻底搞清楚旋转矩阵是怎么回事儿。当然程序中使用的时候推荐使用我上面提供的这种 方法,因为不涉及真实的旋转操作,速度会快很多。通过上面的小例子,我们可以看出越高级别的API帮助我们做的事情就越多,越底层的API提 供了更多的灵活性,但同时也带来了很多需要我们处理的东西。再编程的过程中尽量的使用高级别的API,同时最好能搞懂底层的实现机制。这样我们的程序才会 更高效,出了问题才知道去哪里查找。来自www.cnblogs.com/smileEvday/archive/2013/05/14/UIImage.html

 

你可能感兴趣的文章
数论 - 最小乘法逆元
查看>>
企业架构研究总结(22)——TOGAF架构开发方法(ADM)之信息系统架构阶段
查看>>
接口测试(三)--HTTP协议简介
查看>>
周志华《机器学习》课后答案——第4章.决策树
查看>>
frameset分帧问题
查看>>
特殊样式:ime-mode禁汉字,tabindex焦点
查看>>
linux
查看>>
Layout父元素点击不到的解决办法
查看>>
【面试次体验】堆糖前端开发实习生
查看>>
基于apache实现负载均衡调度请求至后端tomcat服务器集群的实现
查看>>
C#+QQEmail自动发送邮件
查看>>
[Hadoop]MapReduce多输出
查看>>
Android Activity详解(一)
查看>>
快准车服完成3000万元A+轮融资,年底将开始B轮融资
查看>>
让我去健身的不是漂亮小姐姐,居然是贝叶斯统计!
查看>>
MySQL 数据约束
查看>>
我的友情链接
查看>>
SERVLET容器简介与JSP的关系
查看>>
《服务器SSH Public Key认证指南》-补充
查看>>
我的友情链接
查看>>