CATransform3D的坐标系和函数解析

2021-04-14  本文已影响0人  迷路的小小

1. 坐标系

手机坐标系

2. 3D放射矩阵

[                       ]
    m11  m12  m13  m14
    m21  m22  m23  m24
    m31  m32  m33  m34
    m41  m42  m43  m44  
[                       ]

矩阵的计算过程和2D类似,矩阵中每个位置的值对3D仿射效果的作用如下:

平移因子: m41(x) m42(y) m43(z) 
缩放因子: m11(x) m22(y)
切变因子: m21(x) m12(y)
旋转因子: m13(x) m31(y)
透视因子: m34(有旋转才能看出效果)
  //返回一个平移变换的transform3D对象 tx,ty,tz对应x,y,z轴的平移
  CATransform3D CATransform3DMakeTranslation (CGFloat tx, CGFloat ty, CGFloat tz);
  //在某个transform3D变换的基础上进行平移变换,t是上一个transform3D,其他参数同上
  CATransform3D CATransform3DTranslate (CATransform3D t, CGFloat tx, CGFloat ty, CGFloat tz);

新建sb,如图


新建sb
平移实际效果

代码如下:

blueView.layer.borderWidth = 2
blueView.layer.borderColor = UIColor.blue.cgColor
subRedView.layer.transform = CATransform3DTranslate(CATransform3DIdentity, 0, 90, 0)
//x,y,z分别对应x轴,y轴,z轴的缩放比例
  CATransform3D CATransform3DMakeScale (CGFloat sx, CGFloat sy, CGFloat sz);
 //在一个transform3D变换的基础上进行缩放变换,其他参数同上
  CATransform3D CATransform3DScale (CATransform3D t, CGFloat sx, CGFloat sy, CGFloat sz);
缩放实际效果

代码:

blueView.layer.borderWidth = 2
blueView.layer.borderColor = UIColor.blue.cgColor
subRedView.layer.transform = CATransform3DScale(CATransform3DIdentity, 1, 0.5, 1)
//angle参数是旋转的角度,为弧度制 0-2π
//x,y,z决定了旋转围绕的中轴,取值为-1——1之间,例如(1,0,0),则是绕x轴旋转(0.5,0.5,0),则是绕x轴与y轴中
//间45度为轴旋转,依次进行计算
CATransform3D CATransform3DMakeRotation (CGFloat angle, CGFloat x, CGFloat y, CGFloat z);
//在一个transform3D的基础上进行旋转变换,其他参数如上
CATransform3D CATransform3DRotate (CATransform3D t, CGFloat angle, CGFloat x, CGFloat y, CGFloat z);
沿y轴旋转后的结果
let transform = CATransform3DRotate(CATransform3DIdentity, .pi / 2, 0, 1, 0)
blueView.layer.borderWidth = 2
blueView.layer.borderColor = UIColor.blue.cgColor
subRedView.layer.transform = transform
  1. 旋转是以锚点为中心的
  2. 旋转之后坐标系跟随旋转
  3. 无论如何旋转移动子视图永远在父坐标系z>=0的位置

如图下图,绘制一个以y为轴逆时针旋转π/4度,并沿z轴反向偏移90:


π/4

代码如下:

var transform = CATransform3DRotate(CATransform3DIdentity, .pi / 4, 0, 1, 0)
transform = CATransform3DTranslate(transform, 0, 0, -90)
transform.m34 = -1 / 100
blueView.layer.borderWidth = 2
blueView.layer.borderColor = UIColor.blue.cgColor
subRedView.layer.transform = transform
//将一个旋转的效果进行翻转 
CATransform3D CATransform3DInvert (CATransform3D t);

效果如下图所示,此处实际效果为上图沿y轴为中心轴进行翻转,翻转角度与之前一致,实际为原图反向旋转π / 4:


旋转翻转变换

源码如下:

var transform = CATransform3DRotate(CATransform3DIdentity, .pi / 4, 0, 1, 0)
transform = CATransform3DTranslate(transform, 0, 0, -90)
transform = CATransform3DInvert(transform)
blueView.layer.borderWidth = 2
blueView.layer.borderColor = UIColor.blue.cgColor
subRedView.layer.transform = transform

相当于:

transform = CATransform3DRotate(CATransform3DIdentity, .pi / 4, 0, -1, 0)
blueView.layer.borderWidth = 2
blueView.layer.borderColor = UIColor.blue.cgColor
subRedView.layer.transform = transform

旋转翻转变换带来的变化:

翻转变化会使平移变化无效

但在翻转之后使用平移有效

效果如下:


翻转之后的平移

代码如下:

var transform = CATransform3DRotate(CATransform3DIdentity, .pi / 4, 0, 1, 0)

transform = CATransform3DInvert(transform)
transform = CATransform3DTranslate(transform, 0, 0, 90)
blueView.layer.borderWidth = 2
blueView.layer.borderColor = UIColor.blue.cgColor
subRedView.layer.transform = transform
上一篇下一篇

猜你喜欢

热点阅读