Mac App Animation Takeaways
I am developing a Mac App which needs some animations to be done. In fact, I am quite new to animation topics on Mac App. For instance, I have the animation code working in iOS, but I want to port to Mac App. Here are some takeaways in an animation which rotates a layer along x-axis.
Applying 3D Transform
Simply copying the code from iOS, the first problem I faced was the initial transform was not working. I want to set the initial state as 45 degrees rotated, but the layer kept at front-facing position.
I ended up realising that in Cocoa, I have to add the view to the view hierarchy before applying the transform. Without adding as subview, the corresponding view is not rendered. Thus, applying transform has no effect to it.
Transforming all the subviews
While I was looking for solution to the previous problem, I thought it might be the problem of not having CALayer-backed by default. I even thought may be I could not apply the transform to the root layer of the corresponding view.
I ended up knowing that if I created another CALayer for the transform, and inserted this layer to the layer hierarchy. Only this layer will be transformed, and all the subviews like NSTextField will keep unchanged. Another finding is that, this layer can be transformed before the root view is added to view hierarchy.
Comparing iOS animation API
In iOS, animation can be done using the ‘UIView.animateWithDuration()’ API. The method allows me to set duration, delay, damping factors, as well as a completion block. However, this nice API or similar is not available in Cocoa.
I ended up using ‘CABasicAnimation’ to animate the rotation, and then use ‘CATransaction’ to apply completion block. I can optionally use delegate methods to get noticed when animation is complete, but I think completion block makes the code more clear.
Animating the transform
As mentioned, I use CABasicAnimation to animate the rotation. It is making use of the keyPath. Since I want the layer to rotate along x-axis, I have to use “transform.rotation.x”. The API is fairly simple, but it is not Swifty enough. The use of keyPath is not type-safe.
Upon Swift 3, there will be huge improvements to this kind of APIs. The APIs for Swift 3 have become stable. This will be officially available in Xcode 8 public release.
Here is the sample playground for this post.
References:
How to apply a view transformation that works for a UIView to a NSView?
Rotating CALayer of NSImageView 90 degrees
I am taking a challenge to write a post every day for 180 days. The content will be related to my life as a father, entrepreneur, developer and trainer.