CoreAnimation编程指南(三)几何变换

本章介绍图层的几何组成部分,及他们之间的相互关,同时介绍如何变换矩阵可以产生复杂的视觉效果。

一、图层的坐标系

1.图层的坐标系在不同平台上面具有差异性。在iOS系统中,默认的坐标系统原点在图层的中心左上角地方,原点向右和向下为正值。在Mac OS X系统中,默认的坐标系原点在图层的中心左下角地方,原点向右和向上为正值。坐标系的所有值都是浮点类型。你在任何平台上面创建的图层都采用该平台默认的坐标系。

2.每个图层定义并维护自己的坐标系,它里面的全部内容都由此相关的坐标系指定位置。该准则同时适应于图层自己的内容和它的任何子图层。因为任何图层定义了它自己的坐标系,CALayer类提供相应的方法用于从一个图层坐标系的点、矩形、大小值转化为另一个图层坐标系相应的值。

3.一些基于图层的属性使用单元坐标空间测量它们的值。单元坐标空间指定图层边界的相对值,而不是绝对值。单元坐标空间给定的x和y的值总是在0.0到1.0之间。指定一个沿X轴的值为0.0的点,得到的是图层左边缘的一个点,而指定一个1.0的点,则是图层右边缘的一个点。(对 Y轴而言,如果是在iOS系统,则0.0对应于顶部的点,而1.0则是底部的点,而在Mac OS X系统,得到的刚好相反,就如之前提到的坐标系不同一样)。而点(0.5,0.5)则刚好是图层的中心点。
 
二、指定图层的几何

1.虽然图层和图层树与视图和视图的结构在很多方面具有相似性,但是图层的几何却不同,它更加简单通俗。图层的所有几何属性,包括图层的矩阵变换,都可以隐式和显式动画。
  下图显示可以在上下文中指定图层几何的属性:
   CoreAnimation编程指南(三)几何变换 - 米安格 - 米安格的博客
 
2.图层的position属性是一个CGPoint的值,它指定图层相当于它父图层的位置,该值基于父图层的坐标系。

3.图层的bounds属性是一个CGRect的值,指定图层的大小(bounds.size)和图层的原点(bounds.origin)。当你重写图层的重画方法的时候,bounds的原点可以作为图形上下文的原点。

4.图层拥有一个隐式的frame,它是position,bounds,anchorPoint和transform属性的一部分。设置新的frame将会相应的改变图层的position和bounds属性,但是frame本身并没有被保存。但是设置新的frame时候,bounds的原点不受干扰,bounds的大小变为frame的大小,即bounds.size=frame.size。图层的位置被设置为相对于锚点(anchor point)的适合位置。当你设置frame的值的时候,它的计算方式和position、bounds、和anchorPoint的属性相关。

5.图层的anchorPoint属性是一个CGPoint值,它指定了一个基于图层bounds的符合位置坐标系的位置。锚点(anchor point)指定了bounds相对于position的值,同时也作为变换时候的支点。锚点使用单元空间坐标系表示,(0.0,0.0)点接近图层的原点,而(1.0,1.0)是原点的对角点。改变图层的父图层的变换属性(如果存在的话)将会影响到anchorPoint的方向,具体变化取决于父图层坐标系的Y轴。

6.当你设置图层的frame属性的时候,position会根据锚点(anchorPoint)相应的改变,而当你设置图层的position属性的时候,bounds会根据锚点(anchorPoint)做相应的改变。

7.iOS 注意:以下示例描述基于Mac OS X的图层,它的坐标系原点基于左下角。在iOS上面,图层的坐标系原点位于左上角,原点向下和向右为正值。这变化用具体数值显示,而不是概念描述。
下图描述了基于锚点的三个示例值:
  CoreAnimation编程指南(三)几何变换 - 米安格 - 米安格的博客

  anchorPoint默认值是(0.5,0.5),位于图层边界的中心点(如上图显示),B点把anchorPoint设置为(0.0,0.5)。最后C点(1.0,0.0)把图层的position设置为图层frame的右下角。该图适用于Mac OS X的图层。在iOS系统里面,图层使用不同的坐标系,相应的(0.0,0.0)位于左上角,而(1.0,1.0)位于右下角。
    
8.图层的frame、bounds、position和anchorPoint关系如下图所示:
 CoreAnimation编程指南(三)几何变换 - 米安格 - 米安格的博客
 
  在该示例中,anchorPoint默认值为(0.5,0.5),位于图层的中心点。图层的position值为(100.0,100.0),bounds为(0.0,0.0,120,80.0)。通过计算得到图层的frame为(40.0,60.0,120.0,80.0)。

9.如果你新创建一个图层,则只有设置图层的frame为(40.0,60.0,120.0,80.0),相应的position属性值将会自动设置为(100.0,100.0),而bounds会自动设置为(0.0,0.0,120.0,80.0)。
下图显示一个图层具有相同的frame(如上图),但是在该图中它的anchorPoint属性值被设置为(0.0,0.0),位于图层的左下角位置。
 CoreAnimation编程指南(三)几何变换 - 米安格 - 米安格的博客
 
10.图层的frame值同样为(40.0,60.0,120.0,80.0),bounds的值不变,但是图层的position值已经改变为(40.0,60.0)。

11.图层的几何外形和Cocoa视图另外一个不同地方是,你可以设置图层的一个边角的半径来把图层显示为圆角。图层的cornerRadius属性指定了重绘图层内容,剪切子图层,绘制图层的边界和阴影的时候时候圆角的半径。

12.图层的zPosition属性值指定了该图层位于Z轴上面位置,zPosition用于设置图层相对于图层的同级图层的可视位置。
 
三、图层的几何变换-概述

1.图层一旦创建,你就可以通过矩阵变换来改变一个图层的几何形状。CATransform3D的数据结构定义一个同质的三维变换(4×4 CGFloat值的矩阵),用于图层的旋转,缩放,偏移,歪斜和应用的透视。

2.图层的两个属性指定了变换矩阵:transform和sublayerTransform属性。图层的transform属性指定的矩阵结合图层的anchorPoint属性作用于图层和图层的子图层上面。图 3显示在使用anchorPoint默认值(0.5,0.5)的时候旋转和缩放变换如何影响一个图层。而图4显示了同样的矩阵变换在anchorPoint为(0.0,0.0)的时候如何改变一个图层。图层的sublayerTransform属性指定的矩阵只会影响图层的子图层,而不会对图层本身产生影响。

3.你可以通过以下的任何一个方法改变CATransform3D的数据结构:
(1)使用CATransform3D函数
(2)直接修改数据结构的成员
(3)使用键-值编码改变键路径

4.CATransform3DIdentity是单位矩阵,该矩阵没有缩放、旋转、歪斜、透视。把该矩阵应用到图层上面,会把图层几何属性修改为默认值。
 
四、图层的集合变换-变换函数

1.使用变换函数可以在核心动画里面在操作矩阵。你可以使用这些函数(如下表)去创建一个矩阵一般后面用于改变图层或者它的子图层的transform和sublayerTransform属性。变换函数或者直接操或者返回一个CATransform3D的数据结构。这可以让你能够构建简单或复杂的转换,以便重复使用。

2.CATransform3D 变换函数 :偏移、旋转和缩放
(1)CATransform3DMakeTranslation
  Returns a transform that translates by ‘(tx, ty, tz)’. t’ = [1 0 0 0; 0 1 0 0; 0 0 1 0; tx ty tz 1].
(2)CATransform3DTranslate
  Translate ‘t’ by ‘(tx, ty, tz)’ and return the result: * t’ = translate(tx, ty, tz) * t.
(3)CATransform3DMakeScale
  Returns a transform that scales by `(sx, sy, sz)’: * t’ = [sx 0 0 0; 0 sy 0 0; 0 0 sz 0; 0 0 0 1].
(4)CATransform3DScale
  Scale ‘t’ by ‘(sx, sy, sz)’ and return the result: * t’ = scale(sx, sy, sz) * t.
(5)CATransform3DMakeRotation
  Returns a transform that rotates by ‘angle’ radians about the vector ‘(x, y, z)’. If the vector has length zero the identity transform is returned.
(6)CATransform3DRotate
  Rotate ‘t’ by ‘angle’ radians about the vector ‘(x, y, z)’ and return the result. t’ = rotation(angle, x, y, z) * t.
 
3.旋转的单位采用弧度(radians),而不是角度(degress)。以下两个函数,你可以在弧度和角度之间切换。
  CGFloat DegreesToRadians(CGFloat degrees) {return degrees * M_PI / 180;};
  CGFloat RadiansToDegrees(CGFloat radians) {return radians * 180 / M_PI;};
  
4.核心动画提供了用于转换矩阵的变换函数CATransform3DInvert。一般是用反转点内转化对象提供反向转换。当你需要恢复一个已经被变换了的矩阵的时候,反转将会非常有帮助。反转矩阵乘以逆矩阵值,结果是原始值。

5.变换函数同时允许你把CATransform3D矩阵转化为CGAffineTransform(仿射)矩阵,前提是CATransform3D矩阵采用如下表示方法。

6.CATransform3D 与 CGAffineTransform 转换
(1)CATransform3DMakeAffineTransform
  Returns a CATransform3D with the same effect as the passed affine transform.
(2)CATransform3DIsAffine
  Returns YES if the passedCATransform3D can be exactly represented an affine transform.
(3)CATransform3DGetAffineTransform
  Returns the affine transform represented by the passedCATransform3D.
 
7.变换函数同时提供了可以比较一个变换矩阵是否是单位矩阵,或者两个矩阵是否相等。

8.CATransform3D 相等测试
(1)CATransform3DIsIdentity
  Returns YES if the transform is the identity transform.
(2)CATransform3DEqualToTransform
  Returns YES if the two transforms are exactly equal..
 
五、图层的集合变换-修改变换的数据结构

1.你可以修改CATransform3D的数据结构的元素为任何其他你想要的数据值。下面代码包含了CATransform3D数据结构的定义,结构的成员都在其相应的矩阵位置。
  struct CATransform3D
  {
    CGFloat m11, m12, m13, m14;
    CGFloat m21, m22, m23, m24;
    CGFloat m31, m32, m33, m34;
    CGFloat m41, m42, m43, m44;
  };
  typedef struct CATransform3D CATransform3D;
  
2.下面代码中的示例说明了如何配置一个CATransform3D一个角度变换
  CATransform3D aTransform = CATransform3DIdentity;
  //the value of zDistance affects the sharpness of the transform.
  zDistance = 850;
  aTransform.m34 = 1.0 / -zDistance;
  
六、图层的集合变换-通过键值路径修改变换

1.核心动画扩展了键-值编码协议,允许通过关键路径获取和设置一个图层的CATransform3D矩阵的值。下面描述了图层的transform和sublayerTransform属性的相应关键路径。
(1)rotation.x
  The rotation, in radians, in the x axis.
(2)rotation.y
  The rotation, in radians, in the y axis.
(3)rotation.z
  The rotation, in radians, in the z axis.
(4)rotation
  The rotation, in radians, in the z axis. This is identical to setting the rotation.z field.
(5)scale.x
  Scale factor for the x axis.
(6)scale.y
  Scale factor for the y axis.
(7)scale.z
  Scale factor for the z axis.
(8)scale
  Average of all three scale factors.
(9)translation.x
  Translate in the x axis.
(10)translation.y
  Translate in the y axis.
(11)translation.z
  Translate in the z axis.
(12)translation
  Translate in the x and y axis. Value is an NSSize or CGSize.

2.你不可以通过Objective-C 2.0的属性来设置结构域的值,比如下面的代码将会无法正常运行:
  myLayer.transform.rotation.x=0;
 
3.替换的办法是,你必须通过setValue:forKeyPath:或者valueForKeyPath:方法,具体如下:
  [myLayer setValue:[NSNumber numberWithInt:0] forKeyPath:@"transform.rotation.x"];

转自梦维:http://www.dreamingwish.com/dream-2012/coreanimation-programming-guide-c-the-geometric-transformation.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/500111.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

队列和栈

栈 一张图可以简单的说明 为了达到时间复杂度最低:选择的是python列表实现栈,而列表是顺序表 入栈push的时候选择在列表的尾部进行添加元素,出栈在列表尾部弹出 class Stack(object):"""栈"""def __init__(…

CoreAnimation编程指南(四)图层树结构

图层不但给自己提供可视化的内容和管理动画,而且充当了其他图层的容器类,构建图层层次结构。 本章介绍了图层层次结构,以及如何操纵该图层层次结构。一、什么是图层树的层次结构1.图层树是核心动画里面类似Cocoa视图的层次结构。比如一个NSVi…

学习散列表

回顾一下简单查找和二分查找 杂货店商品对应的价格举例: 简单查找就是拿出商品价目本,这个价目本并不是有序的,顾客问苹果多少钱,需要一个一个去查找某一个商品的价格,需要O(n)时间。 同样是一个价目本,但…

CoreAnimation编程指南(五)图层内容

当我们使用Cocoa的视图的时候,我们必须继承NSView或者UIView并且重载函数drawRect:来显示任何内容。但是CALayer实例可以直接使用,而无需继承子类。因为CALayer是一个键-值编码兼容的容器类,你可以在实例里面存储任意值,所以子类实…

SHA算法

回顾散列算法 我的上篇文章:学习散列表 在上篇文章杂货铺的示例中,我们希望散列函数的结果是均匀分布的。散列函数接受一个字符串,并返回一 个索引号。 安全散列算法(secure hash algorithm, SHA)函数 给…

python实现搜索之二分查找

搜索 搜索是在一个项目集合中找到一个特定项目的算法过程。搜索通常的答案是真的或假的,因为该项目是否存在。 搜索的几种常见方法:顺序查找、二分法查找、二叉树查找、哈希查找 二分法查找 二分查找又称折半查找,优点是比较次数少&#x…

CoreAnimation编程指南(九)图层布局

NSView提供了经典的“stuts and springs”模式,用于视图调整大小的时候把关联到它父图层的视图重新调整位置。图层支持该模式,而且Mac OS X上面的核心动画提供了一个更通用的布局管理器机制,允许开发者自己写他们自己的布局管理器。可以为图层…

数据库优化、数据库基础等常用知识点总结

建表优化 1)数据库范式 第一范式(1NF):强调的是列的原子性,即列不能够再分成其他几列。 如电话列可进行拆分—家庭电话、公司电话第二范式(2NF):首先是 1NF,另外包含两…

一片文章概括大部分python面试基础常考题(部分有详解)

本片文章部分参考地址:https://segmentfault.com/a/1190000018737045 python是动态解释性的强类型定义语言 强类型:不允许不同类型相加。例如:整形字符串会报类型错误。 动态:不使用显示数据类型声明,且确定一个变量…

经典逻辑编程题(本文用python实现)

在一个二维数组中(每个一维数组的长度相同),每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序。请完成一个函数,输入这样的一个二维数组和一个整数,判断数组中是否含有该整数。 思…

CoreData简介

一、概念 1.Core Data 是数据持久化存储的最佳方式 2.数据最终的存储类型可以是:SQLite数据库,XML,二进制,内存里,或自定义数据类型 3.好处:能够合理管理内存,避免使用sql的麻烦,高效…

NSZombieEnabled使用

我们做iOS 程序开发时经常用遇到 EXC_BAD_ACCESS 错误导致 Crash,出现这种错误时一般 Xcode 不会给我们太多的信息来定位错误来源,只是在应用 Delegate 上留下像Thread 1: Program received signal:"EXC_BAD_ACCESS",让问题无从找起…

通过终端,查看sqlite3的存储文件

在调试应用的时候,可以查看数据库里的数据。 1、定位到模拟器的目录 cd ~/Library/Application\ Support/iPhone\ Simulator 2、查找文件名包含 OrgChart.sqlite的文件,并打印路径 find . -name "OrgChart.sqlite" –print 输出: .…

iOS的事件分发

移动平台上的开发主要关注数据以及数据的处理,事件的处理以及UI。所以事件的分发处理是很重要的一个环节,对于一个平台的优劣来说也是一项重要的参数。如果事件的分发设计的不好,一些复杂的UI场景就会变得很难写甚至没法写。从小屏没有触摸的…

iOS开发ARC入门和使用

本文部分实例取自iOS 5 Toturail一书中关于ARC的教程和公开内容,仅用于技术交流和讨论。请不要将本文的部分或全部内容用于商用,谢谢合作。 欢迎转载本文,但是转载请注明本文出处:http://www.onevcat.com/2012/06/arc-hand-by-han…

UIBezierPath 的使用介绍

使用UIBezierPath类可以创建基于矢量的路径。此类是Core Graphics框架关于path的一个封装。使用此类可以定义简单的形状,如椭圆或者矩形,或者有多个直线和曲线段组成的形状。1.Bezier Path 基础UIBezierPath对象是CGPathRef数据类型的封装。path如果是基…

iOS中的XML解析

解析方式分类: 解析 XML 通常有两种方式,DOM 和 SAX:DOM解析XML时,读入整个XML文档并构建一个驻留内存的树结构(节点树),通过遍历树结构可以检索任意XML节点,读取它的属性和值。 iOS中XML解析是…

iOS中bundle的使用

一、概述1.在我们使用第三方框架时,常常看到XXX.bundle的文件。我们找到该文件,显示包内容,大致看到很多资源文件:图片、配置文本、XIB文件……2.什么是Bundle文件:简单理解,就是资源文件包。我们将许多图片…

CoreData 自定义数据类型

在CoreData中,Entity中Attribute的类型只有固定的几种可选。如下图: 如果我们要想直接存放UIImage到数据库,如何做? 1.在coredata中新建的attribute中类形选择Transformable. 意思表示这个字段是自定义的类型。 2.在生成的NSMana…

CoreData并发操作模式简介

iOS5.0中,苹果为CoreData的并发处理添加了两个内容。一、首先介绍第一个内容:CoreData框架中的NSManagedObjectContext类增加新的初始化方法:initWithConcurrencyType:(NSManagedObjectContextConcurrencyType)ct;1.参数方法介绍:…