Animation is one of the cornerstones of the UI experience on iOS and thanks to the animation APIs in UIKit (very helpful in 3D configurator processes), it`s incredibly easy. But if you fall down to the core animation layer, it`s possible to create even more dynamic and impressive animations that can help highlight your application. In this article, we explain concepts that Core Animation works in iOS, how to work with the API, and examples of what types of animations and effects it can enable in your application.

professional pics core animation

It will go here in a first step over advanced graphics with core animation.

Before we begin, a few remarks:

As a by-product, we are working on a DRM-free comic reader app for iOS: iComics. The goal is to buy comics from the internet, plug them into your iOS device and read them everywhere. There are websites that serve to republish old comics that have lost their copyright status, as well as new sites (e. g. Humble Bundle and Image Comics). On the Japanese site there is Mangatoshokan Z, where you can buy comics in DRM-free format.

It`s a challenge: if you have an application based on user input, you usually can`t tell in which format the input data will be. Sometimes it`s small, but often it`s big and needs to be handled before it can be effectively rendered on an iOS device. So over the years, we`ve spent a lot of time playing with different techniques: Image scaling, image rendering and playing with core animation to make it work.

In the following article, we`d like to show you everything we`ve learned from our experience.

Note: We are pleased to have been able to use iComics Realm. It`s definitely worth a recommendation.

Overview.

  1. Introduction to Core Animation and how it differs from UIKit. This includes the CA layout object and which effects you can apply to these layer objects to create new effects (not possible with UIKit).
  2. APIs: What APIs are available and what effects can you achieve.
  3. CA layer subclass APIs and GPU level effects.

What is Core Animation?

Core Animation is one of my favorite frameworks in iOS. The API hasn`t changed much between Objective-C and Swift, but it`s the kind of framework many developers don`t know about because it`s not necessary when developing applications. But once you know how to use it, you can get great effects.

Core Animation was introduced in iOS 10 as an optional component. You can choose if you want this performance for your graphics. In iOS, however, it is one layer lower than UIKit, but an integral part of the system.

It is the graphics rendering and animation system available in iOS and is deeply integrated into UIKit. Many properties in UIKit, especially in UIView objects, are mapped directly to properties in Core Animation. Both are connected to each other: Accessing a property in one would automatically update the property in the other.

Core Animation is not executed on the CPU. Your commands are transferred more to the GPU and used to create the graphics displayed on the screen that are supported by the GPU hardware.

We like to think of it as a kind of game development. Back when we modified the game engines, the UI was on the same hierarchy. They had a number of GPU-based squares and quads on the screen. That is, texture bitmap polygons and you would manipulate them on the GPU. If you are already familar with low-level programming, many features in Core Animation will seem familar to you. So it will be easier to work with the graphics hardware if you understand it.

But, it is possible to develop a game on Core Animation? Here Disney can be included in the consideration, who have already realized several games with Core Animation. No game engine, no Unity and no Unreal. If you turn on the debugging mode, you can even see the layer shapes and transformations in real time.

Why is it helpful to learn more about Core Animation?

This is not a basic framework to look when creating apps. You can create functional and well-designed applications without needing them. However, it helps them improve the quality of their applications by understanding what happens naturally in the backend and how content is drawn on the screen.

This can be very useful if you are creating UI layouts that may be more complex than normal. If you have mixed many effects and layers on the top of each other, performance can drop dramatically if you don`t know what you`re doing or where the bottlenecks are. In this case, by learning more about how the systems works, you can optimize your animations and graphics to ensure your applications run at 60 frames per second (FPS). Also, the scope of Core Animation`s functionality exposed to UIKit is limited. You can do more by falling down to this layer and accessing the APIs yourself.

What about Core Graphics?

Core Animation is supposed to be the graphics system of the framework, but there are also Core Graphics.

Core Graphics is completely on the GPU and cannot be executed on the GPU. Since it is a fully CPU-bound operation, it is sometimes slower on older devices. This is something you should keep in mind when using it in your applications. But the good thing about Core Graphics is that you can combine it with Core Animation.

You can use Core Graphics to create the actual bitmaps and use Core Animation to display them to create some cool effects. A cool and remmendable desktop application is PaintCode, which allows you to import graphics or even draw freehand in the application itself and will create the necessary code to render this content in Core Graphics.

It consists of a number of layout objects. The basic class that represents these layout objects is the CALayer class. It looks similar to how UIViews are implemented. If you look at the code below and execute it, you will see a red square on the screen. One of the well-known properties of CALayer is this .cornerRadius property to achieve a nice rounded edge effect.

Copy to Clipboard

Where is it in UIKit?

Everything you see when you view a UIView is not done at the UIView level, but through a back layer attached to this view.

Copy to Clipboard

Everything you see is done by a CALayer, while the layer provides the visual content, UIView offers other things on the UIKit level (order layout functionality, touch detection, guest detection). All this is introduced by UIKit through the layout.

Deeply integrated with UIView.

CALayer and UIView are tightly integrated. Many times when you interact with the UIView, you implicity affect the properties of the underlying layout. For example, if you change the .frame property in a view, you manipulate the borders and center properties on the underlying layer, which are then implicity returned as the .frame property of the view.

Copy to Clipboard

Although I don`t expect the actual implementation of UIView the look like this, many of the UIView level properties are simple access overrides that manipulate the properties for the underlying layer.

Why isn`t it a superclass?

Why is UIView not a subclass of CALayer? Why is the layer exposed to a property in UIView instead?

In addition to CALayer, Apple also offers subclasses (tile and gradient layers). You can insert them into a UIView subclass by swapping out which layer type is exposed by this property. This is a model that would not have been possible if UIView were just a subclass of CALayer. Suppose you wanted to crate a UIView subclass that displays a dynamic gradient. It`s very easy if you override the -layerClass property of the view and specify a CAGradientLayer instead.

Copy to Clipboard

Map content to CALayer.

It`s very easy to create a red quad on the screen, but it`s boring. Instead, it is possible to map a bitmap to a layer by accessing the .contents property (see code example):

Copy to Clipboard

This is very similar to an UIimageView. We can export the “Try!Swift” logo that we previously generated with Core Graphics, export it as UIimage, convert it to a CGImage and apply it directly to the content property of the layer.

Manage CALayer content.

Another cool thing is that the .contents property is animatable, which can have some cool effects. It is possible to configure a layer to change the appearance of the bitmap depending on the size of the frame of the layer itself.

This property is called .contentsGravity and behaves similar to the content mode on the UIView layer. The default value is kCAGravityResize: Regardless of the size of the frame, the image is distorted and squeezed to exactly the same size. If you change the setting to kCAGravityResizeAspectFill, the aspect ratio of the image remains the same, but it is scaled to fill the entire layer and everything outside the region is simply ignored. Switching to kCAGravityResizeAspect ensures that the image remains in its normal aspect ratio and is visible within the frame, regardless of size. When set to center (kCAGravityCenter), the image is not resized but placed in the center of the frame, regardless of its size.

What kind of effects are possible in iOS with this skill?

  • One of the best apps, Tweetbot, uses this functionality in a cool way: When the content scrolls down, the image in the background becomes larger. The width of the frame does not change, only the height. When the frame gets larger, the image is enlarged by filling the layer so that it fits into the same aspect ratio.
  • We found a good way to use this skill from CALayers in thr app, iComics. When iOS 7 came out, there was a shift in the design of the iOS apps to be minimal. So we wanted the slider graphics in our own app to be transparent and the background still visible from behind. Two elements had to work together: the background layer with the page numbers and a transparent handle button that the user manipulated. But how do you cut out the part of the number layer directly behind the sliding head? The solution turned out to be very simple: you render an instance of the number graphic and then apply it to two separate layers on both sides of the button. If you set the content gravity of the left plane to the left (kCAGravityLeft) and the right plane to the right (kCAGravityRight), if you manipulate your frames around the slide button, you get the illusion that they don`t change any position.

Since this methode uses the GPU, it is incredibly performant. There are other ways you could have done this. For example, with a masking layer or in Core Graphics. But, because both would have levered the COU, it would have been slower.

Masking CALayer objects.

Mask CALayer objects: take a layer and set it as the mask property of another layer.

Bitmap sampling in CALayer.

Core Animation also displays settings that allow you to configure which resampling algorithms the GPU uses. Whenever you resize a layer and the size no longer matches the original size of the associated bitmap, resampling must be performed to ensure that it does not look jagged or distorted.

By default, the sampling mode used by Core Animation is called Bilinear Filtering (kCA FilterLinear), a simple linear interpolation between two pixels. Sometimes even bilinear filtering is too slow. If you quickly resize a frame during animation, you may experience problems.

In cases where you change a frame quickly, it`s best to set it nack to the nearest one (kCAFilterNearest). The nearest mode completely disables pixel sampling. In cases where you have mad a layer very large or very small, no sampling will be applied and you will only get a moderate result. In some cases, the animation will run so fast that you often don`t realize the need for better performance.

The last mode is called trilinear filtering (kCAFilterTrilinear), where the GPU creates different sized versions of the same bitmap and joins them together to resize the texture. This can lead to slowdowns because a CPU element is involved – it depends on the needs, but you can get better resampling quality this way.

A good example of where the next filtering in iOS can be useful is opening and closing animations for applications. When an application is closed, it is not only rescaled very quickly, but also faded back to the original system. This combination can lead to FPSuttering on older devices. This means that while the animation is running fast, you can use the next filter and it is not very visible to the user.

Copy to Clipboard

A layer is cut off from this mask, but is still functional, interactive and animable. For iComics, we wanted to create a tutorial view that explains what a setting in App does. We used PaintCode to create a series of images and an alpha channel mask to merge those images. The cool thing about the final effect is that it doesn`t matter what color or pattern the background has. It works on any background, even when scrolling. It is a dynamic safe and useful effect.

Add shadows to CALayer.

Another common effect in iOS is the use of shadows. What would be a long and exhausting process, Core Animation makes it easy to create dynamic shadows and attach them to any shape.

The following code will indeed represent a shadow. However, since the systems needs to perform a pro-pixel comparison to determine the size of the shadow, it will be incredibly slow in terms of rendering and animation.

Copy to Clipboard

Therefore, whenever you work with shadows in Core Animation, you should set the -shadowPath property. This property tells Core Animation in advance the shape of the shadow, reducing render time.

Transform CALayer.

Core Animation also provides a Transform property on CALayer. Unline the Transform property in UIView, which is pure 2D, the Transform property in CALayer provides 3D transformations.

Copy to Clipboard

While the design paradigm for iOS 7 is seemingly flat and minimal, there are cases in the system where 3D transformations are used. The best known example of a third-party application that uses this effect is the Flipboard app. Flipboard uses 3D transformations to create a flip-back effect when you switch between items in its application. While this is not possible in the UIView layer, it is easy in the Core Animation layer.

Blend modes with CALayer.

The ability to ad CALayers blend modes is a cool thing in Core Animation, but uses some private system APIs. Although I can`t officialy recommend this, it`s still cool to look at it. However, it would be very easy to hide it. If you want to consider it for an official application, it`s a possibility.

Copy to Clipboard

For example, if you have two layers and set the top layer as the screen blend mode, you get this effect when the top layer is added to the bottom layer.

One day I got curious and decided to reverse engineer the slide to unlock UIView within iOS. It is not a simple gradient as most people would assume. There is a subtle fractal shimmer effect. I wondered how many layers it had. Five layers, as it turns out.

The top layer is a mask blend layer that pinches everything onto its alpha channel. The next layer is a flat base color that serves as the background for the effect. The next three layers are gradient layers that produce a wedge-shaped highlight shine and a highlight color. The last layer is the most complicated. It is an outline of the text, dashed, blurred, superimposed to create this shimmering effect when mixed with the gradients.

If you look at the official slide to unlock view, Reveal is a very useful tool. Reveal is a debugging tool that lets you check the views of your application from the device on your Mac as you run it. This is especially valuable if you are developing an application with a complex user interface and need to debug it in real time. I couldn’t have done this self-observation without it.

Animate with Core Animation.

How do you implement animations in Core Animation and how do you compare them to the UIView animation APIs in the UIKit layer? I’ll start by implementing animations on the UIKit layer and then show them how to fall down to the Core Animation layer.

Compare with UIKit.

Copy to Clipboard

On the UIKit level it is easy to create an animation. All you need to do is call a method and you will provide a completion that modifies the properties you want to animate; optionally, you will provide a second completion that will be executed once the animation is finished. Core Animation is trickier and requires more code and management.

CABasicAnimation.

Compared to the previous UIKit example, you need to create a CABasicAnimation object and fill it with all the necessary parameters to create a similar effect in Core Animation. Once the object is created, add it to the layer object to start the animation.

Copy to Clipboard

When you create an animation in UIKit, it is done in the background. You can access these animations via the .animationsKeys property of the layer.

Timing function.

One of the main advantages of creating animations at the Core Animation level is that you can create custom timing functions to control the timing of an animation. A good source for this is the CubicBezier.com website. On this website you can directly manipulate an animation timing function and get the floating point values that you can copy directly into Core Animation.

Copy to Clipboard

This allows you to manipulate the speed over time as an animation runs with extremely high precision.

Animate CALayer content.

This allows you to animate the content property of a CALayer.

Copy to Clipboard

If you had an image and wanted to fade it to another image, you would create two views and animate the respective fade; one from 100% alpha to 0%, the other from 0% alpha to 100%. However, when both layers reach an opacity of 50%, there is a short moment when you can see through both. This creates a dimming effect that is easy for the human eye to capture. If you then animate the Content property of a CALayer, you will get a fade effect without this dimmable artifact. This is useful for animations where both images are transparent, as the dimming effect is more pronounced in this case. This visual style is more than iOS 7 – it’s changed to iOS 8.

CAKeyframeAnimation.

CAKeyframeAnimation is a powerful class – you can chain multiple animation points within an object. But that’s not all: Each keyframe point can be assigned a CG Path object that lets you create animations that are not only linear point-to-point transitions, but also curves.

Copy to Clipboard

CAAnimationGroup.

While you can add multiple animations within an object in the UIKit layer, you must create multiple CABasicAnimation objects in Core Animation. If this is the case, you can create your animation objects and add them to a CA animation group object that controls timing (thus making animation control more efficient).

Copy to Clipboard

Handling animation completion.

Similar to UIKit-animations, here also a completion is considered, which will be done after finishing the animation.

Copy to Clipboard

As you can see, there is code that needs to be written if you want to write animations on the Core Animation layer. Similar to PaintCode, there is another application, Core Animator: you create the animations in the application itself and create the corresponding Core Animation code, which you can then copy into your application. It will probably save you a lot of time in the long run.

Features of the Core Animation subclasses.

In iOS, Apple offers a variety of CLS subclasses with many different features.

Some of these subclasses rely on the CPU for the operations you perform. It may be necessary to test them on specific devices to ensure that they meet their specific requirements.

To insert a CLS subclass into a UIView, simply insert the UIView subclass and then override its Layer Class property.

Copy to Clipboard

CATileLayer.

Tile layers are an elementary part of the vector-based drawing on iOS. They automatically manage a grid of tile regions and manage the asynchronous drawing of content to these regions via Core Graphics. When placed in a zoom scroll view, they can be configured to redraw the content at a much higher resolution when zoomed in. This is very useful for displaying content that can be dynamically rendered in any resolution. For example, text in a PDF file or topology information in a mapping application.

CAGradientLayer.

CAGradientLayer is a simple layer in the fact that it only takes a series of dots and colors to create a dynamic gradient effect. The gradient is created on the GPU – it’s incredibly fast. It is often used on other planes that have been transformed into 3D to increase depth perception.

CAReplicaterLayer.

The next CLS subclass is one that resembles a thumbnail tiling effect in the iOS 7 music app. With CAReplicaterLayer, you can specify a layer and have one duplicated multiple times on the GPU. The copies can then be customized. For example, change their color or position to create amazing effects. Since everything is done on the GPU, it’s much faster than trying to start this system manually.

CAShapeLayer.

The next example is one highlighted in the example “slide to unlock”. With CAShapeLayer you can insert a CG path property and visually customize it. For example, it’s very easy to create a circle that you can either fill in completely or add a dash. This layer is useful for creating dynamic effects that match the iOS 7 design style. It’s recommended to try it out and also some of the library people have already built on GitHub, e.g. UAProgressView.

CAEmitterLayer.

As seen in the Disney app, this layer serves as a particle emitter that emits other layers that are configured to be animated in a certain way. It’s not quite clear why this effect exists, but I feel it was probably for OS 10, where there are certain particle effects when you perform actions in the Dock, like pulling out an icon.

You can of course add these effects to your own application if you want a magical note or transitions. If you want to work with a CA middle layer, the Particle Playground application can be recommended. Available from the Mac App Store, you can configure your particle settings with a visual preview and export the lot as a class, which you can then copy directly into your application.

Other layer subclasses.

There are a few other classes available, but we haven’t tested them yet and you can quickly get the feeling that most of them are not suitable for iOS because they are more focused on OS 10 capabilities:

CATextLayer that behaves similar to UILabel, except that it renders the text at the top of the frame instead of in the middle. However, because we have UILabels in iOS and they have things like job layout. It is recommended to use them whenever you can.

CSScrollLayer is probably more OS 10 oriented because we have UIScrollView on iOS, but it’s the same functionality that lets you scroll large amounts of content.

Unlike the already mentioned Transform property, we manipulated a layer in 2D space, with CATransformLayer you can completely manipulate a layer in 3D space and create effects such as rotating cubes. A good example is the old iBooks Store animation in iOS 5.

Two types of layers that are low-level GPU layers: CAEAGLayer and CGAMetallLayer. Both allow you to set up a rendering context by performing low-level graphic rendering. This is the layer they use when you create a game and want direct access to the GPU to write their own rendering code and bypass core animation.

Conclusions.

Try to work first on the UIView plane and if you hit an instance where you can’t get the control you want, then drop down to the core animation level. As long as you understand how UIView and Core Animation work, even if you have to compromise, you should sacrifice 60 frames per second for the desired animation a few times.

While Core Animation offers more control and functionality, it is also more code that needs to be written and maintained. I always recommend that you first try to achieve the desired effect in UIKit.

Thank you for visiting.