Better workaround for unsatisfiable layout constraints for initially zero-sized view?
autolayout, ios
Solution
I think your particular problem stems from attempting to set "container" sizing constraints on an instance of `UITableViewHeaderFooterView`. The issue is similar to wanting to have cells size themselves based on auto layout asked here.
For this question specifically, the view has a size of zero, yet the constraints dictate the view be at least 12pt on a dimension (which violates the current state). This is especially violated in this case and cannot be dealt with due to the header/footer view being sized using frames/autoresizing-masks and not auto-layout, thus the exception.
You have two options for this case:
- Make your constraints less "required" like you suggested in the second part of your question by making the constraints have a priority less than 1000.
- Defer the installation of your constraints until the header/footer has a defined size. You already know your view is going to have a size and that your constraints make sense. Your constraints simply don't make sense to the system for a view that is less than 12pt on an edge (horizontally, in your case). You could hack it together by:
- Checking out `layoutSubviews` for a non-zero `bounds.size`, or (if you're not doing it already)
- Install your constraints (only once) in `updateConstraints` of your `UITableViewHeaderFooterView` subclass.
- You could also combine the two above solutions and only install your auto-layout constraints in `updateConstraints` if you detect that `self.bounds.size` is not `CGSizeZero` (this would be the proper solution).
Problem
Though not consequential it is quite annoying to see these warnings: ``` Unable to simultaneously satisfy constraints. Probably at least one of the constraints in the following list is one you don't want. Try this: (1) look at each constraint and try to figure out which you don't expect; (2) find the code that added the unwanted constraint or constraints and fix it. (Note: If you're seeing NSAutoresizingMaskLayoutConstraints that you don't understand, refer to the documentation for the UIView property translatesAutoresizingMaskIntoConstraints) ( "<NSLayoutConstraint:0x19288a20 V:|-(6)-[UILabel:0x19288640] (Names: '|':_UITableViewHeaderFooterContentView:0x192885b0 )>", "<NSLayoutConstraint:0x19288a70 V:[UILabel:0x19288640]-(6)-| (Names: '|':_UITableViewHeaderFooterContentView:0x192885b0 )>", "<NSAutoresizingMaskLayoutConstraint:0x19289cd0 h=--& v=--& V:[_UITableViewHeaderFooterContentView:0x192885b0(0)]>" ) Will attempt to recover by breaking constraint <NSLayoutConstraint:0x19288a70 V:[UILabel:0x19288640]-(6)-| (Names: '|':_UITableViewHeaderFooterContentView:0x192885b0 )> ``` There is nothing wrong of my constraints. The issue occurs when UIKit tries to do layout for the `UITableViewHeaderFooterView` with these constraints when the view is initially of zero size. Of course it is impossible to satisfy any constraints with any positive metrics. One obvious workaround is to set a lower-than-`UILayoutPriorityRequired` priority or use `NSLayoutRelationLessThanOrEqual` instead of `NSLayoutRelationEqual` for each positive metrics. But then I need to add these crutches to all of my constraints on all of my views. Not to mention that what I really want are hard and fast not optional constraints. Another workaround is to set a initial frame for `UITableViewHeaderFooterView`. But considering its designate init method is `-initWithReuseIdentifier:` not `-initWithFrame:` and it is the responsibility of `UITableView` and `UITableViewDelegate` to specify frame for `UITableViewHeaderFooterView`, it neither feels a good workaround. So any better ones?