Compression Resistance and Content Hugging
As the name suggests, compression resistance refers to the way a view protects its content. A view with a high compression resistance fights against shrinking. It won’t allow that content to clip. Consider the buttons on the toolbar in Figure 1-8. Both screenshots show an application responding to a constraint that wants to set that button width to 40 points.
Figure 1-8 Compression resistance describes how a view attempts to maintain its minimum intrinsic content size. The button at the top of this figure has a high compression resistance.
In Figure 1-8, the top version of the button uses a high compression resistance priority value, and the bottom version uses a low value. As you can see, the higher priority ensures that the top button succeeds in preserving its intrinsic content. The resistance of the bottom button is too low. The resizing succeeds, and the button compresses, clipping the text.
The bottom button’s “don’t clip” request (that is, the compression resistance priority) is still there, but it’s not important enough to prevent the “please set the width to 40” constraint from resizing the view to the button’s detriment. Auto Layout often comes across two conflicting requests. When only one of those requests can win, it satisfies the one with the higher priority.
You specify a view’s compression resistance through IB’s Size Inspector (which you open by selecting View > Utilities > Show Size Inspector > View > Content Compression Resistance Priority), as shown in Figure 1-9, or by setting a value in code. Set the value separately for each axis, horizontal and vertical. Values may range from 1 (lowest priority) to 1,000 (required priority), and the default is 750:
Figure 1-9 Adjust a view’s Content Compression Resistance Priority and Content Hugging Priority settings in IB’s Size Inspector or through code. Although these numbers are presented as a scale of positive integers in IB, they’re actually typed as floats: typedef float UILayoutPriority (iOS) and NSLayoutPriority (OS X). The new Intrinsic Size pop-up enables you to override sizes for placeholder items, so you can test your layout with varied configurations. Compression resistance defaults to 750.
[button setContentCompressionResistancePriority:500 forAxis:UILayoutConstraintAxisHorizontal];
In IB, this is also where you set a view’s content hugging priority. This refers to the way a view prefers to avoid extra padding around its core content (as shown here) or stretching of that core content (as with an image view that uses a scaled content mode). The buttons in Figure 1-10 are being told to stretch. The button at the top has a high content hugging priority, so it resists that stretching. It hugs to the content (in this case, the words Application Button). The button at the bottom has a lower content hugging priority, and the request to stretch wins out. The button pads its contents and produces the wide result you see.
Figure 1-10 Content hugging describes a view’s desire to match its frame to the natural size of its content. A strong hugging priority limits the view from growing much larger than the content it presents. A weak priority may allow a view to stretch and isolate its content among a sea of padding. Because of iOS 7’s borderless buttons, I’ve added a light background tint to the button to highlight extents.
As with compression resistance, you set a view’s hugging priority in IB’s Size Inspector (refer to Figure 1-9) or in code, like this:
[button setContentHuggingPriority:501 forAxis:UILayoutConstraintAxisHorizontal]
Content hugging defaults to 250.