1

I am struggling with the strange issue like when I am adding scale transformation to any layer, it doesn't animated from the center. It does from origin.

func addSquareBorderLayer() {

    borderLayer = CAShapeLayer()
    let rect = CGRect(x: spotlight!.frame.origin.x, y: spotlight!.frame.origin.y, width: spotlight!.frame.width, height: spotlight!.frame.height)
    borderLayer?.path = UIBezierPath(roundedRect: rect, cornerRadius: spotlight!.cornerRadius).cgPath
    borderLayer?.strokeColor = UIColor(red: 91/255, green: 186/255, blue: 162/255, alpha: 1).cgColor //ColorRGB(91, 186, 162)
    borderLayer?.lineWidth = spotlight!.cornerRadius
    borderLayer?.fillColor = UIColor.clear.cgColor
    layer.addSublayer(borderLayer!)

    animatePulsatingLayer(pulsatingLayer: layer)
}

private func animatePulsatingLayer(pulsatingLayer : CALayer) {
    let animation = CABasicAnimation(keyPath: "transform.scale")
    animation.duration       = 0.5
    animation.repeatCount    = .greatestFiniteMagnitude
    animation.autoreverses   = true
    animation.fromValue      = 1
    animation.toValue        = 1.05
    pulsatingLayer.add(animation, forKey: "pulsing")
}

Can anybody please help?

Refernce to what's happening: https://www.dropbox.com/s/0hqdrrv310du7vz/mo.mov?dl=0

Sohil R. Memon
  • 9,404
  • 1
  • 31
  • 57
  • Possible duplicate of [CALayer - CABasicAnimation not scaling around center/anchorPoint](https://stackoverflow.com/questions/11495956/calayer-cabasicanimation-not-scaling-around-center-anchorpoint). Set the `bounds` of your CAShapeLayer to something nonzero, like a rect with origin zero and size `spotlight.frame.size`. – Kurt Revis Dec 28 '18 at 22:39
  • @KurtRevis I have tried all the possible solution on SO. Thanks – Sohil R. Memon Dec 29 '18 at 05:49

1 Answers1

0

It's a bit tricky. You need to set the frame for the layer as the rect you are setting currently for path. And set path origin to zero so that the circle(or any shape) is drawn at the same position as frame's origin. This will allow the animation to be applied at the anchorPoint (0.5, 0.5).

Here is the complete example,

var borderLayer: CAShapeLayer!

func addSquareBorderLayer() {

    let size: CGFloat = 100

    borderLayer = CAShapeLayer()
    let rect = CGRect(origin: .zero, size: CGSize(width: size, height: size))
    borderLayer?.path = UIBezierPath(roundedRect: rect, cornerRadius: 50).cgPath
    borderLayer?.strokeColor = UIColor(red: 91/255, green: 186/255, blue: 162/255, alpha: 1).cgColor
    borderLayer?.lineWidth = 20
    borderLayer?.fillColor = UIColor.clear.cgColor
    borderLayer?.frame = CGRect(origin: CGPoint(x: 100, y: 200), size: rect.size)
    self.view.layer.addSublayer(borderLayer!)

    animatePulsatingLayer(pulsatingLayer: borderLayer!)
}

private func animatePulsatingLayer(pulsatingLayer : CALayer) {
    let animation = CABasicAnimation(keyPath: "transform.scale")
    animation.duration       = 0.3
    animation.repeatCount    = .greatestFiniteMagnitude
    animation.autoreverses   = true
    animation.fromValue      = 1
    animation.toValue        = 1.2
    pulsatingLayer.add(animation, forKey: "pulsing")
}

Result

enter image description here

Kamran
  • 14,987
  • 4
  • 33
  • 51