Swift - 根据其内容自动布局 UILabel 高度

Posted

技术标签:

【中文标题】Swift - 根据其内容自动布局 UILabel 高度【英文标题】:Swift - auto layout UILabel height based on its contents 【发布时间】:2020-01-11 11:38:12 【问题描述】:

我在为 UILabel 设置自动布局时遇到问题,希望获得这方面的帮助。

在图片中,我创建了黄色和绿色的 UILabel。

我想要实现的是根据其内容的行数动态调整黄色 UILabel 的高度,并将绿色框的顶部锚定到黄色框的底部。

目前,我的代码如下:

// Yellow UILabel
addSubview(captionLabel)
captionLabel.anchor(top: actionButtonsStackView.bottomAnchor, left: leadingAnchor, bottom: nil, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)
captionLabel.heightAnchor.constraint(greaterThanOrEqualToConstant: 0).isActive = true

// Green UILabel
addSubview(dateLabel)
dateLabel.anchor(top: captionLabel.bottomAnchor, left: leadingAnchor, bottom: bottomAnchor, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)

注意:anchor 函数设置 top、leading、bottom 和 trailing 具有各自填充的约束。

如您所见,黄色 UILabel 占用的空间比它实际需要的要多。

如果我离开绿色 UILabel 的顶部约束,黄色框实际上开始按我的预期工作:

这个代码看起来像:

// Yellow UILabel
addSubview(captionLabel)
captionLabel.anchor(top: actionButtonsStackView.bottomAnchor, left: leadingAnchor, bottom: nil, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)
captionLabel.heightAnchor.constraint(greaterThanOrEqualToConstant: 0).isActive = true

// Green UILabel
addSubview(dateLabel)
dateLabel.anchor(top: nil, left: leadingAnchor, bottom: bottomAnchor, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)

我在这里做错了什么?


实际上,从绿色框中删除 bottomAnchor 使其工作:

这个代码看起来像:

// Yellow UILabel
addSubview(captionLabel)
captionLabel.anchor(top: actionButtonsStackView.bottomAnchor, left: leadingAnchor, bottom: nil, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)
captionLabel.heightAnchor.constraint(greaterThanOrEqualToConstant: 0).isActive = true

// Green UILabel
addSubview(dateLabel)
dateLabel.anchor(top: captionLabel.bottomAnchor, left: leadingAnchor, bottom: nil, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)

但它为什么有效?我想通过设置更大的ThenOrEqual 常量,黄色的UILabel 自动调整大小以容纳其内容,而绿色的UILabel 会根据bottomAnchor 的黄色UILabel 调整其大小。

【问题讨论】:

greaterThenOrEqual 不会阻止“拉伸”。它确实可以防止收缩超过某个值,但这不是您想要的。内容拥抱和内容压缩阻力根据您为这些值提供的优先级确定视图是否应该拉伸或收缩。 另外,要给出一个有效的答案,红框是如何配置的?它是否有固定的高度限制,它的优先级是什么? 红框暂时固定高度 【参考方案1】:

那是因为您要添加两个具有相同垂直内容拥抱优先级的标签(默认为low)。如果希望绿色标签更高,可以将红色标签的Content Hugging Priority 值设置为highrequired。代码如下:

// Yellow UILabel
addSubview(captionLabel)
captionLabel.setContentHuggingPriority(.defaultHigh, for: .vertical)
captionLabel.anchor(top: actionButtonsStackView.bottomAnchor, left: leadingAnchor, bottom: nil, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)

// Green UILabel
addSubview(dateLabel)
dateLabel.anchor(top: captionLabel.bottomAnchor, left: leadingAnchor, bottom: bottomAnchor, right: trailingAnchor, paddingTop: 0, paddingLeft: 8, paddingBottom: 0, paddingRight: 8, width: 0, height: 0)

更多详情可以这篇文章:https://medium.com/@abhimuralidharan/ios-content-hugging-and-content-compression-resistance-priorities-476fb5828ef

【讨论】:

以上是关于Swift - 根据其内容自动布局 UILabel 高度的主要内容,如果未能解决你的问题,请参考以下文章

根据自动布局更改 UILabel 中的字体大小(swift)

使用故事板、自动布局和 Swift 的多行 UILabel 和 UITextView

如何在启用自动布局的情况下根据 UILabel 的内容自动更改 UILabel 对象的高度和下方其他元素的位置

具有自动布局的多行UILabel,如何在不更改标签框架的情况下根据内容调整字体大小?

自动布局在 x 轴上居中 uilabel 适合内容,uiimage 跟随在左侧

多行 UILabel 和 UIScrollview 使用自动布局