将CATransform3DMakeRotation应用于CAShapeLayer后重新调整坐标系

问题描述 投票:0回答:1

我正在开发一个应用程序,用户可以在其中编辑使用CAShapeLayer创建的不同形状。一切正常,直到我旋转或翻转形状。当我应用这些转换时,坐标系似乎也发生了变化。此后,其他转换(例如CATransform3DMakeTranslation)将无法正常工作。

如何重新调整坐标系?是否可以在保持原始坐标系的同时翻转/旋转形状?

这是一个示例,我想将形状旋转45度,然后将其向上移动100点。如果在移动形状之前将其旋转,则该形状将向右而不是向上移动。

class ViewController: UIViewController {
    @IBOutlet weak var canvasView: UIView!

    override func viewDidLoad() {
        super.viewDidLoad()

        // Create path

        let path = UIBezierPath()
        path.move(to: CGPoint(x: canvasView.bounds.midX, y: canvasView.bounds.maxX))
        path.addLine(to: CGPoint(x: canvasView.bounds.midX, y: canvasView.bounds.minY))

        // Create shape layer

        let shapeLayer = CAShapeLayer()
        shapeLayer.frame = canvasView.bounds
        shapeLayer.path = path.cgPath
        shapeLayer.strokeColor = UIColor.black.cgColor
        shapeLayer.fillColor = UIColor.clear.cgColor
        shapeLayer.lineWidth = 8.0
        shapeLayer.lineCap = .round
        shapeLayer.lineJoin = .round
        canvasView.layer.addSublayer(shapeLayer)

        // Add transformations to shape layer

        var transform = CATransform3DMakeRotation(0.785398, 0.0, 0.0, 1.0)
        transform = CATransform3DTranslate(transform, 0.0, -100.0, 0.0)

        shapeLayer.transform = transform
    }
}
ios swift core-animation calayer cashapelayer
1个回答
0
投票

CATransform3DMakeScale

it返回按sxsysz缩放的变换,其中sxsysz是缩放,乘以x,y和z坐标。当您使用2d对象(例如UIlabel z参数)不会影响您的对象时:

例如,如果要用1/2 x,3 * y转换对象,应编写如下:

myObject.layer.transform = CATransform3DMakeScale(0.5, 3.0, 1.0)

enter image description here

旋转

旋转变换使图层围绕锚点旋转(默认情况下为图层的中心)。基本语法是:

CATransform3DMakeRotation(angle: CGFloat, x: CGFloat, y: CGFloat, z: CGFloat)

其中,角度是弧度,层应旋转的角度,x,y和z是旋转轴。将轴设置为0会取消围绕该特定轴的旋转。

如果我们想将图层顺时针旋转30度,我们将执行以下操作:

let degrees = 30.0
let radians = CGFloat(degrees * M_PI / 180)
myObject.layer.transform = CATransform3DMakeRotation(radians, 0.0, 0.0, 1.0)

enter image description here

您仅可以为每个图层设置一个变换,因此,如果要使用多个变换,则应使用多重变换

** CATransform3DConcat **

为了组合多个变换,我们可以使用像这样的隐喻

CATransform3DConcat(a: CATransform3D, b: CATransform3D)

但是,我们将一个接一个地做。第一个转换将使用Make作为其名称。以下转换将不使用Make,但它们会将先前的转换作为参数。

let firstTransform = CATransform3DMakeScale(0.5, 3.0, 1.5)

let degrees = 30.0
let radians = CGFloat(degrees * M_PI / 180)
let second = CATransform3DMakeRotation(radians, 0.0, 0.0, 1.0)
myObject.layer.transform = CATransform3DConcat(firstTransform, second)

此外,我们可以一个接一个地插入它们作为级联变换层

let degrees = 30.0
let radians = CGFloat(degrees * M_PI / 180)

// translate
var transform = CATransform3DMakeTranslation(90, 50, 0)

// rotate
transform = CATransform3DRotate(transform, radians, 0.0, 0.0, 1.0)

// scale
transform = CATransform3DScale(transform, 0.5, 3.0, 1.0)

// apply the transforms
myObject.layer.transform = transform

enter image description here

© www.soinside.com 2019 - 2024. All rights reserved.