UITableViewCell自动计算高度时的约束警告

具体业务

UITableViewCell 中嵌套一个 UICollectionView,Cell 的高度需要根据 CollectionView items 个数动态变化

image

遇到的问题

最后实现的效果是没有问题的,但会出现这样的约束警告

[LayoutConstraints] 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. 
[
    <MASLayoutConstraint:0x600002c6e6a0 UILabel:0x7ffc5fcf4bc0.top == XBHDemandRegionHotCitiesCell:0x7ffc611b3a00.top + 15>,
    <MASLayoutConstraint:0x600002c6ed60 UICollectionView:0x7ffc60a93c00.top == UILabel:0x7ffc5fcf4bc0.bottom + 5>,
    <MASLayoutConstraint:0x600002c6edc0 UICollectionView:0x7ffc60a93c00.bottom == XBHDemandRegionHotCitiesCell:0x7ffc611b3a00.bottom - 10>,
    <MASLayoutConstraint:0x600002c6efa0 UICollectionView:0x7ffc60a93c00.height == 70>,
    <NSLayoutConstraint:0x600002b52c60 DemandRegionHotCitiesCell:0x7ffc611b3a00.height == 44.3333>
]

Will attempt to recover by breaking constraint 
<MASLayoutConstraint:0x600002c6efa0 UICollectionView:0x7ffc60a93c00.height == 70>

Make a symbolic breakpoint at UIViewAlertForUnsatisfiableConstraints to catch this in the debugger.
The methods in the UIConstraintBasedLayoutDebugging category on UIView listed in <UIKitCore/UIView.h> may also be helpful.

强迫症表示真的不能忍!!!

分析问题的根源

从警告中可以看到,Cell 有一个高度为 44.3333 的高度约束, 与 CollectionView 的高度为70约束产生了冲突,那么Cell的高度为44.3333的高度约束是从何而来的呢?

- (void)setCities:(NSArray<XBHRegion *> *)cities {
    _cities = [cities copy];
    [self.collectionView reloadData];
    NSInteger rowCount = ceil(_cities.count / ColumnCount);
    NSInteger spcingCount = MAX(rowCount - 1, 0);
    CGFloat collectionViewHeight = self.flowLayout.minimumLineSpacing * spcingCount + self.flowLayout.itemSize.height * rowCount;
    [self.collectionView mas_updateConstraints:^(MASConstraintMaker *make) {
        make.height.mas_equalTo(collectionViewHeight);
    }];
}

更新 CollectionView 的高度是在上述代码中实现的,那么初次赋值时,cities的个数为0,导致 Cell 高度为 44.3333
所以猜想在cities有值时,系统在重新 layout 时,并没有把原先 高度为 44.3333 的约束移除,产生了约束冲突警告。

解决思路

Q:如果把这个 UICollectionView 的换成一个 UILabel 会不会产生警告呢?
A:答案当然是不会的,这种业务以前已经做过多次。
Q:那么为什么换成 UILabel 就不会呢?
A:是不是要反过来想,UILabel 是没有设置高度约束的,他是如何确定高度来“撑大” Cell的?

到这里,想必大家已经知道答案了。UILabel 是根据其内容来自动计算大小的,也就是intrinsicContentSize,转换为约束的优先级是 ContentHuggingPriority 默认是 750,而我们给 UICollectionView 添加的高度约束默认是 1000 的, 那么改一下不就ok了!

 make.height.mas_equalTo(collectionViewHeight).priorityMedium()

大功告成!!!

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 1、通过CocoaPods安装项目名称项目信息 AFNetworking网络请求组件 FMDB本地数据库组件 SD...
    阳明AI阅读 16,019评论 3 119
  • 绩效管理解决的问题主要包括: (1)如何确定有效的目标? (2)如何使目标在管理者与员工之间达成共识? (3)如何...
    晶晶_f6dd阅读 163评论 0 0
  • 这满目的红霞,好似我灵魂的家。窗外的清风带着现实的味道吹在我麻木的身上。祝安好!
    美妖Emma阅读 236评论 0 1
  • 你有那么多面,为什么偏偏把最不好的一面展示给了最亲的人? 我们评价一个人,往往做不到全面,因为我们无法真正地完完全...
    诺feiyang阅读 539评论 1 2
  • 呼 把那个放了几年的小木箱拿了出来 已经积灰了 再打开时 发现点点滴滴都是与她的回忆 毕竟分开也已经有好几年了 那...
    Jimniy阅读 107评论 0 1