11

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?

an0
  • 17,191
  • 12
  • 86
  • 136

1 Answers1

12

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:

  1. 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.
  2. 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:
    1. Checking out layoutSubviews for a non-zero bounds.size, or (if you're not doing it already)
    2. Install your constraints (only once) in updateConstraints of your UITableViewHeaderFooterView subclass.
    3. 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).
Community
  • 1
  • 1
larsacus
  • 7,346
  • 3
  • 26
  • 23
  • What solution do you recommend for people using Interface Builder? – Josh Bernfeld Jan 28 '16 at 01:53
  • 1
    @walapu You will probably want to go with #1 above and give your view less rigid (priority <1000) constraints in order for it to not throw an exception in the `CGSizeZero` case. – larsacus Jan 28 '16 at 16:25
  • 1
    I wound up going with this solution http://stackoverflow.com/a/35053234/1275014 because setting less rigid constraints would work but not with UILabels – Josh Bernfeld Jan 29 '16 at 03:22