Looking for best practices of using layout anchors? Let's learn how to use the iOS autolayout system in the proper way using Swift.
Creating views and constraints programmatically
First of all I'd like to recap the UIViewController life cycle methods, you are might familiar with some of them. They are being called in the following order:
In the pre-auto layout era, you had to do your layout calcuations inside the
viewDidLayoutSubviews method, but since this is a pro auto layout tutorial we are only going to focus on the
viewDidLoad methods. 🤓
These are the basic rules of creating view hierarchies using auto layout:
- Never calculate frames manually by yourself! ⚠️⚠️⚠️
- Initialize your views with
- Add your view to the view hierarchy using
- Create and activate your layout constraints
viewDidLoadfor creating views with constraints
- Take care of memory management by using
- Set every other property like background color, etc. in
Enough theory, here is a short example:
Pretty simple, huh? Just a few lines of code and you have a fixed size center aligned view with a dedicated class property reference. If you create the exact same through interface builder, the system will "make" you the
loadView method for free, but you'll have to setup an
IBOutlet reference to the view.
The eternal dilemma: code vs Interface Builder.
It really doesn't matters, feel free to chose your path. Sometimes I love playing around with IB, but in most of the cases I prefer the programmatic way of doing things. 😛
Common UIKit auto layout constraint use cases
So I promised that I'll show you how to make constraints programmatically, right? Let's do that now. First of all, I use nothing but layout anchors. You could waste your time with the visual format language, but that's definitely a dead end. So mark my words: use only anchors or stack views, but nothing else! 😇
Here are the most common patterns that I use to create nice layouts. 😉
Set fixed with or height
First one is the most simple one: set a view's height or a width to a fixed point.
Set aspect ratio
Settings a view's aspect ratio is just constrainting the width to the height or vica versa, you can simply define the rate by the multiplier.
Center horizontally & vertically
Centering views inside another one is a trivial task, there are specific anchors for that.
Stretch | fill inside view with padding
The only tricky part here is that trailing and bottom constraints behave a little bit different, than top & leading if it comes to the constants. Usually you have to work with negative values, but after a few tries you'll understand the logic here. 😅
Proportional width or height
If you don't want to work with constant values, you can use the multiplier.
Using safe area layout guides
With the latest iPhone you'll need some guides in order to keep you safe from the notch. This is the reason why views have the
safeAreaLayoutGuide property. You can get all the usual anchors after calling out to the safe area guide. 💪
Animating layout constraints
Animation with constraints is easy, you shouldn't believe what others might say. I made some rules and an example that'll help you understanding the basic principles of animating constant values of a constraint, plus toggling various constraints. 👍
- Use standard UIView animation with
- Always deactivate constraints first
- Hold to your deactivated constraints strongly
- Have fun! 😛
Constraint animation example:
It's not that bad, next: adaptivity and supporting multiple device screen sizes. 🤔
How to create adaptive layouts for iOS?
Even Apple is struggling with adaptive layouts in the built-in iOS applications. If you look at apps that are made with collection views - like photos - layouts are pretty ok on every device. However there are a few other ones, that - in my opinion - are horrible experiences on a bigger screen. #justusecollectionviewforeverything. 🤐
Your first step to adaptive layout is supporting multiple device orientations. You can check my previous article about iOS auto layout there are lots of great stuff inside that article about rotation support, working with layers inside auto layout land, etc. 🌈
Second step is to adapt trait collections. UITraitCollection is there for you to group all the environmental specific traits such as size classes, display scale, user interface idom and many more. Most of the times you will have to check the vertical & horizontal size classes. There is a reference of device size classes and all the possible variations made by Apple, see the external sources section below. 😉
This little Swift code example below is demonstrating how to check size classes for setting different layouts for compact and regular screens.
You can also check the user interface idom through the
UIDevice class (aka. is this freakin' device an iPhone or an iPad?) to set for example font sizes based on it. 📱
Another option to figure out your environment is checking the size of the screen. You can check the native pixel count or a relative size based in points.
Usually I'm trying to keep myself to these rules. I don't really remember a scenario where I needed more than all the things I've listed above, but if you have a specific case or questions, please don't hesitate to contact me. 😉