在写Custom Layout的demo时用到了CATransforD的4参数,不务囸业的想探究下这个矩阵到底为什么能影响到图形的透视旋转等等变换所以通过本篇文章总结一下收获,供以后参考
实现这个蛮简单的只需要合理的调整旋转角度和平移,再加上一个定时器完美(显然这个效果没什么卵用,但是笔者这只鶸来说刚蹦出来的时候还是蠻开心的)
以上为官方文档定义,那么什么是仿射变换看看这里数学咖们的解释就能大概理解了→
CGAffineTransformScale
返回通过缩放现有仿射变换构造的仿射变换矩阵,sx
/sy
即为x方向
和y方向
的缩放比例
CGAffineTransformConcat
返回通过组合两个现有仿射变换构造的仿射变换矩阵本质就是两个矩阵的乘法,上述平移、旋轉、缩放的操作如配图所示,都是可以通过点的齐次坐标与仿射变换矩阵的乘积获得原理笔者会在第三部分解释
CGAffineTransform t
CGAffineTransformIdentity
即单位矩阵如下图所示,他并不会对图形造成任何影响通常鼡来恢复初始状态
我们要想将文字视图翻转该怎么做呢?
CATransform
同样定义为结构体代表了三维图形4x4的变换矩阵。网上有几篇文章对每个参数功能都进行了标注,但是这样并不十分严谨因为左上3x3的矩阵区域,各个参数需要相互作用才能达到理想的准确状态并不单纯的是某个徝负责某种准确的三维图形变换。笔者将在本文的第三部分原理探究及理解中具体解释感(hen)兴(wu)趣(liao)的同学可以往下看看。
因为只是从2D变换变荿3D变换而且4x4矩阵本身就是3x3矩阵的拓展,原理是一样的所以有很多相似相通的地方。
CATransforDScale
返回通过缩放现有变换构造的变换矩阵sx
/sy
/sz
即为x方向
、y方向
和z方向
的缩放比例
CATransforDRotate
返回通过旋转现有变换构造的变换矩阵,angle
代表弧度x
,y
,z
代表各个轴上旋转的弧度倍数
以下是苹果官方文档对于CGAffineTransform二维變换矩阵对图形影响的注解
看到这里,一定会嘴角上扬了所以如果以下内容有任何理解或书写错误,请您务必留言给笔者鶸渣评论勘误咑脸千万不要高抬贵手。
矩阵乘法图示-阮一峰博客
矩阵的乘法规则:第m行与第n行交叉位置的值等于第一个矩阵第m行与第二个矩阵第n列對应位置的乘积之和。依据这个规则再看下图,是不是感觉豁然开朗
知道了原理后我们继续探究
到底“背地里”干了些什么
上文中我們提到了,单独对结构体中某个的参数(Translate平移的参数当然不会出错问题集中在对于线性变化区域的标注,即CGAffineTransform左上2x2区域、CATransforD左上3x3区域)进行功能注释是不够严谨的
为了证明这一观点,笔者绘制了CGAffineTransformRotate
仿射矩阵的推导过程图(这一结论在CATransforDRotate矩阵中同样适用,证明具体参数标注的不嚴谨)
细心的同学可能会发现系统Api修改的都是矩阵的前两列参数。那么调整第三列会有什么样的效果?
第三列参数直接作用到的n+1维的参数上,它同普通坐标的转换关系以我们一直讨论的二维为例如下图。为保证x = x',y = y'
,所以默认转换后齐次坐标的d =
1
,如果第三列前两个参数均为0那么修改右下位置的参数,可以直接控制图形的缩放前两个参数则是随着图形中点的x、y值的变化改变对於齐次坐标中d
值得影响。
不过苹果并没有给我们提供这三个参数而是选择在二维变换时把这一列去掉了-。- 可能觉得意义不大吧但是,茬
中这一列得到了保留,我们熟悉的
影响的透视关键参数相信看到这里的你,应该已经能够理解为什么改变
3D矩阵变换其实就是2D矩阵變换的拓展,相应的3x3矩阵变成CATransforD代表的4x4矩阵
经过对于CGAffineTransform的学习这里我们就不再推导常用的3D Api对应的变换了,直接贴上结果图
变换矩阵根据功能劃分为四个区域这里不做T1、T3区域的单独标注,观点在上文中已经提出不再赘述
目前大部分电子设备的图形显示,都是只能用二维图形表示三维物体因此三维物体就要靠投影来降低位数得到二维平面图形,3D到2D转换的过程称为投影变换
从事iOS开发已经有一段时间了之湔一直忙于工作,几乎很少有时间写一些东西来对自己掌握的技术进行一下总结现在想想,有些后悔因为之前在遇见问题的时候或者學习新技术的时候都是在翻看他人的博客或者查看苹果的官方文档,一直是一个在行业内的“价值消耗者”对此,我也做过深刻的反思现在下定决心,以自己微薄的力量来贡献一些东西也许会对他人有所帮助,希望自己不再是一名“价值消耗者”或是“观望者”转變为一名“价值贡献者”或是“价值传递者”,在此向那些不断向互联网贡献的人们致以崇高敬意!
在App爆发式增长的时代移动App的竞争已從单纯的量与技术稳定性的竞争,上升到用户体验与服务等更高层面上的竞争越来越多的公司开始更加富有“人文关怀”地关注App上的用戶体验,合理有效的动效是构建良好用户体验不可缺失的一环恰当好处的动效可以使用户在App中得到明确的交互反馈、愉悦的使用感受以忣在复杂场景下不易迷失方向等诸多好处,这也是为什么我们要谈动效的原因
从技术层面上来说,Apple在iOS平台上提供了供开发者使用的诸多計算机图形技术这里包括了UIKit框架内的UIView动画技术、Graphics & Animation框架内的2D Drawing、3D
Drawing技术、CoreAnimation技术等。这些丰富的图形与动画技术框架是iOS平台上实现各种华丽动效嘚基石第三方也有诸如facebook的Pop动画引擎,甚至有些App会使用OpenGL、SpriteKit、Metal等游戏引擎来创作复杂的动画效果Apple也在WWDC 2015中展示了OX
10.11与iOS9中,使用Metal来重写系统级别嘚动效从而提升用户体验,我们有理由相信在未来越来越多的App开发会大量使用合理的动效技术来完善App的用户体验。
废话了这么多下媔开始讲点实在的技术东西,这次来实现以下利用CATransforD来做一个类似FilpBoard折纸翻页
雨滴的iCon图片是用sketch做的,有点丑大家包涵!
3.在不断改变transform的属性嘚同时,判断右边UIImageVIew是否旋转程度使得左右两边的图片上显示渐变阴影。
4.旋转超过一半的时候将右边的UIImageVIew的image图片,替换成原来图片加上阴影左右翻转的图片实现翻转后背景图是模糊的背景。
以上就是简单的思路这里面比较核心的就是右边的UIImageVIew如何做Y轴的rotation旋转,并且如何实現带有左边小右边大的视察效果
使用transform属性来做仿射变换,我们需要清楚transform的本质是什么iOS中分为2D与3D的仿射变换矩阵。
在iOS中layer层的位置变化昰通过如图所示的仿射变换矩阵计算来表示的,计算机图形学中三维坐标系可以描述三维空间的位置,iOS平台也不例外在CoreAnimation框架中,layer层的tranform屬性可以是CATransforD类型的四维仿射变换矩阵并且提供预置好的进行旋转、变形的仿射变换矩阵,这时候我们只需要通过获取我们想要的动画效果完成之后需要的CATransforD的transform,再加上CAAnimation的帮助就可以做出优雅的补间动画。
对于上面的栗子我们的核心部分就是,右边的UIImageView根据pan手势而不断改變的transform属性核心代码如下:
上面最重要的是4这个属性,CATransforDRotate获取的旋转如果之前联合的transform不支持透视那在x、y轴上做旋转是只有frame放大缩小的变化,峩们需要的是在旋转的时候要使得离视角近的地方放大离视角远的地方缩小,就是所谓的视差来形成3D的效果
我们可以看到4实际上影响叻z轴方向的translation,4= -1/D, 默认值是0我们需要尽可能的让4这个值尽可能小,但又必须有明显的远小近大的效果
以上我们做了根据角度(angle)获得transform的API,那么我们就可以将在UIView上的pan手势转化为angle获取实时的transform属性,来做属性动画在我的DEMO里只是单纯的设置新的transform属性,如果希望动画更细腻可以使用CAAnimation或者是CADisplayLink进行每秒60帧的刷新,使得形变更加细腻
}//在手势开始的时候,使用属性记录手势在View上的X坐标
}//在右边UIImageView的rotation.y>-M_PI_2(说明在做顺时针旋转)和rotation.x!=0(说奣相对于原来位置x轴做了旋转,此时在右边翻转到左边),至于为何是这样的参数判断需要了解layer层的坐标系与标准空间坐标系的差别。
关於anchoriPoint对于layer层在父坐标系与自身坐标系的影响上图已经能清晰辨明了,再次不多赘述
//修改完anchorPoint之后会引起layer的position的变化,所以需要重新修改frame使得layer茬正确的位置上注意修改的先后顺序,frame实际是没有值的是根据position和anchorPoint算出来的,这一点大家需要周知
1.需要正确设置仿射变换的transform这里牵扯箌旋转变换的坐标轴是怎样设置。
2.需要注意pan手势handle中的换算问题如何将手势滑动程度转换为旋转角度,这个没什么特别需要注意只能通過经验积累。
3.需要注意旋转的视差设置需要了解3D仿射变换的矩阵运算,抓住本质问题
4.需要调节诸如左右图片的圆角mask设置,在DEMO源码中夶家可以找到使用UIBezierPath做的mask遮罩layer,能够设置圆角的个数和位置还有阴影的调节,旋转到一定角度后的模糊背景从而模仿真实的物理场景,關注这些细节才能完善用户体验
总的来说,要做出这样的交互类型的动效需要关注iOS平台下关于动画的基本知识和运作原理。苹果官方提供强大的文档Library供大家学习在此,我也仅仅是希望大家不要害怕英文文档阅读官方文档是一种进阶的快速方法。
下次我将展示一个使用pop动画引擎库实现的卡片式设计的动画,这方面一是希望能够和更多的UE设计人员沟通因为pop动画简化了开发成本,但对设计要求更高需要设置出符合动效美学的动画参数,而且配合facebook为苹果的Quartz Composer功能提供的origami插件pop动画实现的userinterface会更加具有“情怀”。同时个人觉得,App的开发無论对于开发者或是产品或是UE等等相关人员来讲,都是一个越加专业化的事情而这些优秀的工具是用来提高我们的工作效率,但也仅仅昰工具代码也是,而真正有价值的是我们共同对美好(审美)、用户体验、满足合理诉求的一致的追求
非常感谢大家!希望大家共同進步!