I’ve talked about it before, but just as a reminder: Constraints are handled as math equations that should only have one and only one possible solution. Sometimes however we make mistakes when constructing them, leaving us with problems, meaning: multiple or not even a single solution to our equations.
We need to be able to identify these problems and solve them properly. That’s exactly what I want to focus this section on.
Types of Errors
Again, like before, I want to introduce you to a little bit to theory first before we dive into solving auto layout issues. Because there are 3 different types of issues that can occur:
- Unsatisfiable Layouts
- Ambiguous Layouts
- Logical Errors
Let’s dive into each of them on its own and I’ll show you exactly what they mean as well as how you can solve them.
First up, there’s Unsatisfiable Layouts. Those are layouts that have no valid solution at all. The problem here is that you might have two constraints that conflict each other, because they can not be true at the same time. You can think of this in a very simple way.
Say we have a view. We have already set a constraint that the views height should be 20. Now if we add a constraint to the view that tells it to be 30 in height, we have an unsatisfiable Layout. The layout can not be solved because there obviously is no solution to making a view 20 and 30 point in height.
- Height of view: 20
- Height of view: 30
So that’s the first problem, the second one is ambiguous layouts. This happens when a layout has two or more possible solutions. This usually happens when auto-layout hasn’t got all the information it needs to solve the layout completely. This would mean that one attribute is not properly defined or that the system has conflicting optionals constraints with the same priority. Both of those cases create a system that can not be solved.
Think of another example: We have a similar view as before and we nest this view inside of another view. Now we set the top and bottom boundaries to be the ones from the superview with a constant of 20. Also we set the superview to be 120 in height. That leaves us with a view that is 80 point high and has a clearly defined X-Position. What this doesn’t have is a set Y position and a width. Even if one of those would be solved we would still have an ambiguous layout because the auto-layout system can not decide where to put the view or how wide it should be.
The last two errors are some that Xcode can help with. There are tools in the Interface Builder that can help manage those errors, find out what’s going wrong and resolve some of the issues. But there is another type of error that unfortunately Xcode can’t help with.
Apple calls them logical errors and frankly that’s exactly what they are. Some people would also call them bugs, because these are issues that can’t be traced back to math. It’s just setting constraints in a way that doesn’t reflect the way constraints work. It usually happens when you have false assumptions about how auto-layout works and set constraints in a senseless way.
Most of the time this happens when dealign with constraints in code, which is another reason I recommend using the Interface Builder when your just starting out.
Now let’s look at all of this theory in action when we use Xcode.
Let’s just create a view in the interface builder as a superview and a view nested inside of the superview. We’re going to set constraints in a way that matches one of our errors. That way I can show you how the tools in the Interface Builder can help us solve our issues.
Right in the top left corner we can see a red or yellow arrow that tells us that we have some issue in our auto-layout constraints. Let’s just go ahead and click that to see what the problem is and what Xcode tells us to do to solve the issue.
As you’ve seen we can have Xcode help us with the constraints quite a bit, but sometimes the messages that Xcode gives us are not super helpful. In this case it is important to know which information Xcode actually needs to resolve an auto-layout properly. We have done that well in the exercises before but I didn’t really tell you the nuts and bolts of it.
It might be obvious, but auto-layout needs 4 informations to layout a view correctly, otherwise you’ll have an ambiguous layout right in front of you.
Those properties are:
- X Position
- Y Position
Those informations can be provided in a variety of ways. For example you could set the width of a button by giving it a fixed width constraint, or you could make use of the leading and trailing properties in correspondence to the outside of the superview to give auto-layout the possibility to make the width of the button variable. Both have different results in the app itself, but what they have in common, is that they determine wich width the button should have.
So when you’re debugging your constraints, just remember to provide all those attributes.