Если вы хотите провести слой вдоль пути:
let segmentDuration: CFTimeInterval = 2.0
let rect = CGRect(x: 0.0, y: 0.0, width: 100.0, height: 100.0)
let path = UIBezierPath(rect: rect)
let posAnimation = CAKeyframeAnimation(keyPath: "position")
posAnimation.duration = segmentDuration
posAnimation.path = path.cgPath
posAnimation.timingFunction = CAMediaTimingFunction(name: CAMediaTimingFunctionName.linear)
posAnimation.calculationMode = .paced
posAnimation.repeatCount = .infinity
anyLayer.add(posAnimation, forKey: "position")
Если вы хотите изменить положение, попробуйте что-то вроде этого:
let segmentDuration: CFTimeInterval = 2.0
let points = [CGPoint(x: 0, y: 0), CGPoint(x: 400.0, y: 0.0), CGPoint(x: 200.0, y: 200.0)]
let posAnimation = CABasicAnimation(keyPath: "position")
posAnimation.duration = segmentDuration
posAnimation.fromValue = points[0]
posAnimation.toValue = points[1]
let posAnimation1 = CABasicAnimation(keyPath: "position")
posAnimation1.beginTime = posAnimation.duration
posAnimation1.duration = segmentDuration
posAnimation1.fromValue = points[1]
posAnimation1.toValue = points[2]
let posAnimation2 = CABasicAnimation(keyPath: "position")
posAnimation2.beginTime = posAnimation.duration + posAnimation1.duration
posAnimation2.duration = segmentDuration
posAnimation2.fromValue = points[2]
posAnimation2.toValue = points[0]
let positionChain: CAAnimationGroup = CAAnimationGroup()
positionChain.animations = [posAnimation, posAnimation1, posAnimation2]
positionChain.duration = posAnimation.duration + posAnimation1.duration + posAnimation2.duration
positionChain.fillMode = CAMediaTimingFillMode.forwards
positionChain.repeatCount = .infinity
anySubLayer.add(positionChain, forKey: "positionChain")
Если вы хотите изменить форму основного слояпросто создайте CAShapeLayer с нужной вам формой, замаскируйте слой и запустите анимацию:
let segmentDuration: CFTimeInterval = 2.0
let rect = CGRect(x: 0.0, y: 0.0, width: 100.0, height: 100.0)
let shapeLayer = CAShapeLayer()
shapeLayer.path = UIBezierPath(rect: rect).cgPath
shapeLayer.frame = CGRect(x: 0, y: 0, width: 10, height: 10)
layer.mask = shapeLayer
let paths = [UIBezierPath(rect: rect), UIBezierPath(roundedRect: rect, cornerRadius: 25), UIBezierPath(ovalIn: rect)]
let pathAnimation = CABasicAnimation(keyPath: "path")
pathAnimation.duration = segmentDuration
pathAnimation.fromValue = paths[0].cgPath
pathAnimation.toValue = paths[1].cgPath
let pathAnimation1 = CABasicAnimation(keyPath: "path")
pathAnimation1.beginTime = pathAnimation.duration
pathAnimation1.duration = segmentDuration
pathAnimation1.fromValue = paths[1].cgPath
pathAnimation1.toValue = paths[2].cgPath
let pathAnimation2 = CABasicAnimation(keyPath: "path")
pathAnimation2.beginTime = pathAnimation.duration + pathAnimation1.duration
pathAnimation2.duration = segmentDuration
pathAnimation2.fromValue = paths[2].cgPath
pathAnimation2.toValue = paths[0].cgPath
let pathChain: CAAnimationGroup = CAAnimationGroup()
pathChain.animations = [pathAnimation, pathAnimation1, pathAnimation2]
pathChain.duration = pathAnimation.duration + pathAnimation1.duration + pathAnimation2.duration
pathChain.fillMode = CAMediaTimingFillMode.forwards
pathChain.repeatCount = .infinity
shapeLayer.add(pathChain, forKey: "positionChain")